| self = <austin.format.mojo.MojoStreamReader object at 0x000001F9C2319D00>
|
|
|
| def parse_event(self) -> t.Optional[MojoEvent]:
|
| """Parse a single event."""
|
| try:
|
| (event_id,) = self.read()
|
| except ValueError:
|
| return None
|
|
|
| try:
|
| > event = t.cast(dict, self.__handlers__)[event_id](self)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
| E KeyError: 13
|
|
|
| venv\Lib\site-packages\austin\format\mojo.py:622: KeyError
|
|
|
| The above exception was the direct cause of the following exception:
|
|
|
| cls = <class '_pytest.runner.CallInfo'>
|
| func = <function FlakyPlugin.call_and_report.<locals>._call_runtest_hook.<locals>.<lambda> at 0x000001F9C2334FE0>
|
| when = 'call'
|
| reraise = (<class '_pytest.outcomes.Exit'>, <class 'KeyboardInterrupt'>)
|
|
|
| @classmethod
|
| def from_call(
|
| cls,
|
| func: Callable[[], TResult],
|
| when: Literal["collect", "setup", "call", "teardown"],
|
| reraise: type[BaseException] | tuple[type[BaseException], ...] | None = None,
|
| ) -> CallInfo[TResult]:
|
| """Call func, wrapping the result in a CallInfo.
|
|
|
| :param func:
|
| The function to call. Called without arguments.
|
| :type func: Callable[[], _pytest.runner.TResult]
|
| :param when:
|
| The phase in which the function is called.
|
| :param reraise:
|
| Exception or exceptions that shall propagate if raised by the
|
| function, instead of being wrapped in the CallInfo.
|
| """
|
| excinfo = None
|
| instant = timing.Instant()
|
| try:
|
| > result: TResult | None = func()
|
| ^^^^^^
|
|
|
| venv\Lib\site-packages\_pytest\runner.py:353:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| > lambda: ihook(item=item, **kwds), when=when, reraise=reraise
|
| ^^^^^^^^^^^^^^^^^^^^^^^^
|
| )
|
|
|
| venv\Lib\site-packages\flaky\flaky_pytest_plugin.py:146:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <HookCaller 'pytest_runtest_call'>
|
| kwargs = {'item': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = False
|
|
|
| def __call__(self, **kwargs: object) -> Any:
|
| """Call the hook.
|
|
|
| Only accepts keyword arguments, which should match the hook
|
| specification.
|
|
|
| Returns the result(s) of calling all registered plugins, see
|
| :ref:`calling`.
|
| """
|
| assert not self.is_historic(), (
|
| "Cannot directly call a historic hook - use call_historic instead."
|
| )
|
| self._verify_all_args_are_provided(kwargs)
|
| firstresult = self.spec.opts.get("firstresult", False) if self.spec else False
|
| # Copy because plugins may register other plugins during iteration (#438).
|
| > return self._hookexec(self.name, self._hookimpls.copy(), kwargs, firstresult)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| venv\Lib\site-packages\pluggy\_hooks.py:512:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <_pytest.config.PytestPluginManager object at 0x000001F9BFCD6000>
|
| hook_name = 'pytest_runtest_call'
|
| methods = [<HookImpl plugin_name='threadexception', plugin=<module '_pytest.threadexception' from 'D:\\a\\austin\\austin\\venv\\...e=None>>, <HookImpl plugin_name='logging-plugin', plugin=<_pytest.logging.LoggingPlugin object at 0x000001F9C0778350>>]
|
| kwargs = {'item': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = False
|
|
|
| def _hookexec(
|
| self,
|
| hook_name: str,
|
| methods: Sequence[HookImpl],
|
| kwargs: Mapping[str, object],
|
| firstresult: bool,
|
| ) -> object | list[object]:
|
| # called from all hookcaller instances.
|
| # enable_tracing will set its own wrapping function at self._inner_hookexec
|
| > return self._inner_hookexec(hook_name, methods, kwargs, firstresult)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| venv\Lib\site-packages\pluggy\_manager.py:120:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| hook_name = 'pytest_runtest_call'
|
| hook_impls = [<HookImpl plugin_name='threadexception', plugin=<module '_pytest.threadexception' from 'D:\\a\\austin\\austin\\venv\\...e=None>>, <HookImpl plugin_name='logging-plugin', plugin=<_pytest.logging.LoggingPlugin object at 0x000001F9C0778350>>]
|
| caller_kwargs = {'item': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = False
|
|
|
| def _multicall(
|
| hook_name: str,
|
| hook_impls: Sequence[HookImpl],
|
| caller_kwargs: Mapping[str, object],
|
| firstresult: bool,
|
| ) -> object | list[object]:
|
| """Execute a call into multiple python functions/methods and return the
|
| result(s).
|
|
|
| ``caller_kwargs`` comes from HookCaller.__call__().
|
| """
|
| __tracebackhide__ = True
|
| results: list[object] = []
|
| exception = None
|
| try: # run impl and wrapper setup functions in a loop
|
| teardowns: list[Teardown] = []
|
| try:
|
| for hook_impl in reversed(hook_impls):
|
| try:
|
| args = [caller_kwargs[argname] for argname in hook_impl.argnames]
|
| except KeyError as e:
|
| # coverage bug - this is tested
|
| for argname in hook_impl.argnames: # pragma: no cover
|
| if argname not in caller_kwargs:
|
| raise HookCallError(
|
| f"hook call must provide argument {argname!r}"
|
| ) from e
|
|
|
| if hook_impl.hookwrapper:
|
| function_gen = run_old_style_hookwrapper(hook_impl, hook_name, args)
|
|
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
|
|
| elif hook_impl.wrapper:
|
| try:
|
| # If this cast is not valid, a type error is raised below,
|
| # which is the desired response.
|
| res = hook_impl.function(*args)
|
| function_gen = cast(Generator[None, object, object], res)
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
| except StopIteration:
|
| _raise_wrapfail(function_gen, "did not yield")
|
| else:
|
| res = hook_impl.function(*args)
|
| if res is not None:
|
| results.append(res)
|
| if firstresult: # halt further impl calls
|
| break
|
| except BaseException as exc:
|
| exception = exc
|
| finally:
|
| if firstresult: # first result hooks return a single value
|
| result = results[0] if results else None
|
| else:
|
| result = results
|
|
|
| # run all wrapper post-yield blocks
|
| for teardown in reversed(teardowns):
|
| try:
|
| if exception is not None:
|
| try:
|
| teardown.throw(exception)
|
| except RuntimeError as re:
|
| # StopIteration from generator causes RuntimeError
|
| # even for coroutine usage - see #544
|
| if (
|
| isinstance(exception, StopIteration)
|
| and re.__cause__ is exception
|
| ):
|
| teardown.close()
|
| continue
|
| else:
|
| raise
|
| else:
|
| teardown.send(result)
|
| # Following is unreachable for a well behaved hook wrapper.
|
| # Try to force finalizers otherwise postponed till GC action.
|
| # Note: close() may raise if generator handles GeneratorExit.
|
| teardown.close()
|
| except StopIteration as si:
|
| result = si.value
|
| exception = None
|
| continue
|
| except BaseException as e:
|
| exception = e
|
| continue
|
| _raise_wrapfail(teardown, "has second yield")
|
|
|
| if exception is not None:
|
| > raise exception
|
|
|
| venv\Lib\site-packages\pluggy\_callers.py:167:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| hook_name = 'pytest_runtest_call'
|
| hook_impls = [<HookImpl plugin_name='threadexception', plugin=<module '_pytest.threadexception' from 'D:\\a\\austin\\austin\\venv\\...e=None>>, <HookImpl plugin_name='logging-plugin', plugin=<_pytest.logging.LoggingPlugin object at 0x000001F9C0778350>>]
|
| caller_kwargs = {'item': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = False
|
|
|
| def _multicall(
|
| hook_name: str,
|
| hook_impls: Sequence[HookImpl],
|
| caller_kwargs: Mapping[str, object],
|
| firstresult: bool,
|
| ) -> object | list[object]:
|
| """Execute a call into multiple python functions/methods and return the
|
| result(s).
|
|
|
| ``caller_kwargs`` comes from HookCaller.__call__().
|
| """
|
| __tracebackhide__ = True
|
| results: list[object] = []
|
| exception = None
|
| try: # run impl and wrapper setup functions in a loop
|
| teardowns: list[Teardown] = []
|
| try:
|
| for hook_impl in reversed(hook_impls):
|
| try:
|
| args = [caller_kwargs[argname] for argname in hook_impl.argnames]
|
| except KeyError as e:
|
| # coverage bug - this is tested
|
| for argname in hook_impl.argnames: # pragma: no cover
|
| if argname not in caller_kwargs:
|
| raise HookCallError(
|
| f"hook call must provide argument {argname!r}"
|
| ) from e
|
|
|
| if hook_impl.hookwrapper:
|
| function_gen = run_old_style_hookwrapper(hook_impl, hook_name, args)
|
|
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
|
|
| elif hook_impl.wrapper:
|
| try:
|
| # If this cast is not valid, a type error is raised below,
|
| # which is the desired response.
|
| res = hook_impl.function(*args)
|
| function_gen = cast(Generator[None, object, object], res)
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
| except StopIteration:
|
| _raise_wrapfail(function_gen, "did not yield")
|
| else:
|
| res = hook_impl.function(*args)
|
| if res is not None:
|
| results.append(res)
|
| if firstresult: # halt further impl calls
|
| break
|
| except BaseException as exc:
|
| exception = exc
|
| finally:
|
| if firstresult: # first result hooks return a single value
|
| result = results[0] if results else None
|
| else:
|
| result = results
|
|
|
| # run all wrapper post-yield blocks
|
| for teardown in reversed(teardowns):
|
| try:
|
| if exception is not None:
|
| try:
|
| > teardown.throw(exception)
|
|
|
| venv\Lib\site-packages\pluggy\_callers.py:139:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <_pytest.logging.LoggingPlugin object at 0x000001F9C0778350>
|
| item = <Function test_fork_cpu_time_cpu_bound[austin-3.14]>
|
|
|
| @hookimpl(wrapper=True)
|
| def pytest_runtest_call(self, item: nodes.Item) -> Generator[None]:
|
| self.log_cli_handler.set_when("call")
|
|
|
| with self._runtest_for(item, "call"):
|
| > yield
|
|
|
| venv\Lib\site-packages\_pytest\logging.py:850:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| hook_name = 'pytest_runtest_call'
|
| hook_impls = [<HookImpl plugin_name='threadexception', plugin=<module '_pytest.threadexception' from 'D:\\a\\austin\\austin\\venv\\...e=None>>, <HookImpl plugin_name='logging-plugin', plugin=<_pytest.logging.LoggingPlugin object at 0x000001F9C0778350>>]
|
| caller_kwargs = {'item': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = False
|
|
|
| def _multicall(
|
| hook_name: str,
|
| hook_impls: Sequence[HookImpl],
|
| caller_kwargs: Mapping[str, object],
|
| firstresult: bool,
|
| ) -> object | list[object]:
|
| """Execute a call into multiple python functions/methods and return the
|
| result(s).
|
|
|
| ``caller_kwargs`` comes from HookCaller.__call__().
|
| """
|
| __tracebackhide__ = True
|
| results: list[object] = []
|
| exception = None
|
| try: # run impl and wrapper setup functions in a loop
|
| teardowns: list[Teardown] = []
|
| try:
|
| for hook_impl in reversed(hook_impls):
|
| try:
|
| args = [caller_kwargs[argname] for argname in hook_impl.argnames]
|
| except KeyError as e:
|
| # coverage bug - this is tested
|
| for argname in hook_impl.argnames: # pragma: no cover
|
| if argname not in caller_kwargs:
|
| raise HookCallError(
|
| f"hook call must provide argument {argname!r}"
|
| ) from e
|
|
|
| if hook_impl.hookwrapper:
|
| function_gen = run_old_style_hookwrapper(hook_impl, hook_name, args)
|
|
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
|
|
| elif hook_impl.wrapper:
|
| try:
|
| # If this cast is not valid, a type error is raised below,
|
| # which is the desired response.
|
| res = hook_impl.function(*args)
|
| function_gen = cast(Generator[None, object, object], res)
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
| except StopIteration:
|
| _raise_wrapfail(function_gen, "did not yield")
|
| else:
|
| res = hook_impl.function(*args)
|
| if res is not None:
|
| results.append(res)
|
| if firstresult: # halt further impl calls
|
| break
|
| except BaseException as exc:
|
| exception = exc
|
| finally:
|
| if firstresult: # first result hooks return a single value
|
| result = results[0] if results else None
|
| else:
|
| result = results
|
|
|
| # run all wrapper post-yield blocks
|
| for teardown in reversed(teardowns):
|
| try:
|
| if exception is not None:
|
| try:
|
| > teardown.throw(exception)
|
|
|
| venv\Lib\site-packages\pluggy\_callers.py:139:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <CaptureManager _method='no' _global_capturing=<MultiCapture out=None err=None in_=None _state='suspended' _in_suspended=False> _capture_fixture=None>
|
| item = <Function test_fork_cpu_time_cpu_bound[austin-3.14]>
|
|
|
| @hookimpl(wrapper=True)
|
| def pytest_runtest_call(self, item: Item) -> Generator[None]:
|
| with self.item_capture("call", item):
|
| > return (yield)
|
| ^^^^^
|
|
|
| venv\Lib\site-packages\_pytest\capture.py:900:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| hook_name = 'pytest_runtest_call'
|
| hook_impls = [<HookImpl plugin_name='threadexception', plugin=<module '_pytest.threadexception' from 'D:\\a\\austin\\austin\\venv\\...e=None>>, <HookImpl plugin_name='logging-plugin', plugin=<_pytest.logging.LoggingPlugin object at 0x000001F9C0778350>>]
|
| caller_kwargs = {'item': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = False
|
|
|
| def _multicall(
|
| hook_name: str,
|
| hook_impls: Sequence[HookImpl],
|
| caller_kwargs: Mapping[str, object],
|
| firstresult: bool,
|
| ) -> object | list[object]:
|
| """Execute a call into multiple python functions/methods and return the
|
| result(s).
|
|
|
| ``caller_kwargs`` comes from HookCaller.__call__().
|
| """
|
| __tracebackhide__ = True
|
| results: list[object] = []
|
| exception = None
|
| try: # run impl and wrapper setup functions in a loop
|
| teardowns: list[Teardown] = []
|
| try:
|
| for hook_impl in reversed(hook_impls):
|
| try:
|
| args = [caller_kwargs[argname] for argname in hook_impl.argnames]
|
| except KeyError as e:
|
| # coverage bug - this is tested
|
| for argname in hook_impl.argnames: # pragma: no cover
|
| if argname not in caller_kwargs:
|
| raise HookCallError(
|
| f"hook call must provide argument {argname!r}"
|
| ) from e
|
|
|
| if hook_impl.hookwrapper:
|
| function_gen = run_old_style_hookwrapper(hook_impl, hook_name, args)
|
|
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
|
|
| elif hook_impl.wrapper:
|
| try:
|
| # If this cast is not valid, a type error is raised below,
|
| # which is the desired response.
|
| res = hook_impl.function(*args)
|
| function_gen = cast(Generator[None, object, object], res)
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
| except StopIteration:
|
| _raise_wrapfail(function_gen, "did not yield")
|
| else:
|
| res = hook_impl.function(*args)
|
| if res is not None:
|
| results.append(res)
|
| if firstresult: # halt further impl calls
|
| break
|
| except BaseException as exc:
|
| exception = exc
|
| finally:
|
| if firstresult: # first result hooks return a single value
|
| result = results[0] if results else None
|
| else:
|
| result = results
|
|
|
| # run all wrapper post-yield blocks
|
| for teardown in reversed(teardowns):
|
| try:
|
| if exception is not None:
|
| try:
|
| > teardown.throw(exception)
|
|
|
| venv\Lib\site-packages\pluggy\_callers.py:139:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| item = <Function test_fork_cpu_time_cpu_bound[austin-3.14]>
|
|
|
| @hookimpl(wrapper=True)
|
| def pytest_runtest_call(item: Item) -> Generator[None]:
|
| xfailed = item.stash.get(xfailed_key, None)
|
| if xfailed is None:
|
| item.stash[xfailed_key] = xfailed = evaluate_xfail_marks(item)
|
|
|
| if xfailed and not item.config.option.runxfail and not xfailed.run:
|
| xfail("[NOTRUN] " + xfailed.reason)
|
|
|
| try:
|
| > return (yield)
|
| ^^^^^
|
|
|
| venv\Lib\site-packages\_pytest\skipping.py:268:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| hook_name = 'pytest_runtest_call'
|
| hook_impls = [<HookImpl plugin_name='threadexception', plugin=<module '_pytest.threadexception' from 'D:\\a\\austin\\austin\\venv\\...e=None>>, <HookImpl plugin_name='logging-plugin', plugin=<_pytest.logging.LoggingPlugin object at 0x000001F9C0778350>>]
|
| caller_kwargs = {'item': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = False
|
|
|
| def _multicall(
|
| hook_name: str,
|
| hook_impls: Sequence[HookImpl],
|
| caller_kwargs: Mapping[str, object],
|
| firstresult: bool,
|
| ) -> object | list[object]:
|
| """Execute a call into multiple python functions/methods and return the
|
| result(s).
|
|
|
| ``caller_kwargs`` comes from HookCaller.__call__().
|
| """
|
| __tracebackhide__ = True
|
| results: list[object] = []
|
| exception = None
|
| try: # run impl and wrapper setup functions in a loop
|
| teardowns: list[Teardown] = []
|
| try:
|
| for hook_impl in reversed(hook_impls):
|
| try:
|
| args = [caller_kwargs[argname] for argname in hook_impl.argnames]
|
| except KeyError as e:
|
| # coverage bug - this is tested
|
| for argname in hook_impl.argnames: # pragma: no cover
|
| if argname not in caller_kwargs:
|
| raise HookCallError(
|
| f"hook call must provide argument {argname!r}"
|
| ) from e
|
|
|
| if hook_impl.hookwrapper:
|
| function_gen = run_old_style_hookwrapper(hook_impl, hook_name, args)
|
|
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
|
|
| elif hook_impl.wrapper:
|
| try:
|
| # If this cast is not valid, a type error is raised below,
|
| # which is the desired response.
|
| res = hook_impl.function(*args)
|
| function_gen = cast(Generator[None, object, object], res)
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
| except StopIteration:
|
| _raise_wrapfail(function_gen, "did not yield")
|
| else:
|
| > res = hook_impl.function(*args)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| venv\Lib\site-packages\pluggy\_callers.py:121:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| item = <Function test_fork_cpu_time_cpu_bound[austin-3.14]>
|
|
|
| def pytest_runtest_call(item: Item) -> None:
|
| _update_current_test_var(item, "call")
|
| try:
|
| del sys.last_type
|
| del sys.last_value
|
| del sys.last_traceback
|
| if sys.version_info >= (3, 12, 0):
|
| del sys.last_exc # type:ignore[attr-defined]
|
| except AttributeError:
|
| pass
|
| try:
|
| > item.runtest()
|
|
|
| venv\Lib\site-packages\_pytest\runner.py:179:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <Function test_fork_cpu_time_cpu_bound[austin-3.14]>
|
|
|
| def runtest(self) -> None:
|
| """Execute the underlying test function."""
|
| > self.ihook.pytest_pyfunc_call(pyfuncitem=self)
|
|
|
| venv\Lib\site-packages\_pytest\python.py:1720:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <HookCaller 'pytest_pyfunc_call'>
|
| kwargs = {'pyfuncitem': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = True
|
|
|
| def __call__(self, **kwargs: object) -> Any:
|
| """Call the hook.
|
|
|
| Only accepts keyword arguments, which should match the hook
|
| specification.
|
|
|
| Returns the result(s) of calling all registered plugins, see
|
| :ref:`calling`.
|
| """
|
| assert not self.is_historic(), (
|
| "Cannot directly call a historic hook - use call_historic instead."
|
| )
|
| self._verify_all_args_are_provided(kwargs)
|
| firstresult = self.spec.opts.get("firstresult", False) if self.spec else False
|
| # Copy because plugins may register other plugins during iteration (#438).
|
| > return self._hookexec(self.name, self._hookimpls.copy(), kwargs, firstresult)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| venv\Lib\site-packages\pluggy\_hooks.py:512:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <_pytest.config.PytestPluginManager object at 0x000001F9BFCD6000>
|
| hook_name = 'pytest_pyfunc_call'
|
| methods = [<HookImpl plugin_name='python', plugin=<module '_pytest.python' from 'D:\\a\\austin\\austin\\venv\\Lib\\site-packages\\_pytest\\python.py'>>]
|
| kwargs = {'pyfuncitem': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = True
|
|
|
| def _hookexec(
|
| self,
|
| hook_name: str,
|
| methods: Sequence[HookImpl],
|
| kwargs: Mapping[str, object],
|
| firstresult: bool,
|
| ) -> object | list[object]:
|
| # called from all hookcaller instances.
|
| # enable_tracing will set its own wrapping function at self._inner_hookexec
|
| > return self._inner_hookexec(hook_name, methods, kwargs, firstresult)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| venv\Lib\site-packages\pluggy\_manager.py:120:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| hook_name = 'pytest_pyfunc_call'
|
| hook_impls = [<HookImpl plugin_name='python', plugin=<module '_pytest.python' from 'D:\\a\\austin\\austin\\venv\\Lib\\site-packages\\_pytest\\python.py'>>]
|
| caller_kwargs = {'pyfuncitem': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = True
|
|
|
| def _multicall(
|
| hook_name: str,
|
| hook_impls: Sequence[HookImpl],
|
| caller_kwargs: Mapping[str, object],
|
| firstresult: bool,
|
| ) -> object | list[object]:
|
| """Execute a call into multiple python functions/methods and return the
|
| result(s).
|
|
|
| ``caller_kwargs`` comes from HookCaller.__call__().
|
| """
|
| __tracebackhide__ = True
|
| results: list[object] = []
|
| exception = None
|
| try: # run impl and wrapper setup functions in a loop
|
| teardowns: list[Teardown] = []
|
| try:
|
| for hook_impl in reversed(hook_impls):
|
| try:
|
| args = [caller_kwargs[argname] for argname in hook_impl.argnames]
|
| except KeyError as e:
|
| # coverage bug - this is tested
|
| for argname in hook_impl.argnames: # pragma: no cover
|
| if argname not in caller_kwargs:
|
| raise HookCallError(
|
| f"hook call must provide argument {argname!r}"
|
| ) from e
|
|
|
| if hook_impl.hookwrapper:
|
| function_gen = run_old_style_hookwrapper(hook_impl, hook_name, args)
|
|
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
|
|
| elif hook_impl.wrapper:
|
| try:
|
| # If this cast is not valid, a type error is raised below,
|
| # which is the desired response.
|
| res = hook_impl.function(*args)
|
| function_gen = cast(Generator[None, object, object], res)
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
| except StopIteration:
|
| _raise_wrapfail(function_gen, "did not yield")
|
| else:
|
| res = hook_impl.function(*args)
|
| if res is not None:
|
| results.append(res)
|
| if firstresult: # halt further impl calls
|
| break
|
| except BaseException as exc:
|
| exception = exc
|
| finally:
|
| if firstresult: # first result hooks return a single value
|
| result = results[0] if results else None
|
| else:
|
| result = results
|
|
|
| # run all wrapper post-yield blocks
|
| for teardown in reversed(teardowns):
|
| try:
|
| if exception is not None:
|
| try:
|
| teardown.throw(exception)
|
| except RuntimeError as re:
|
| # StopIteration from generator causes RuntimeError
|
| # even for coroutine usage - see #544
|
| if (
|
| isinstance(exception, StopIteration)
|
| and re.__cause__ is exception
|
| ):
|
| teardown.close()
|
| continue
|
| else:
|
| raise
|
| else:
|
| teardown.send(result)
|
| # Following is unreachable for a well behaved hook wrapper.
|
| # Try to force finalizers otherwise postponed till GC action.
|
| # Note: close() may raise if generator handles GeneratorExit.
|
| teardown.close()
|
| except StopIteration as si:
|
| result = si.value
|
| exception = None
|
| continue
|
| except BaseException as e:
|
| exception = e
|
| continue
|
| _raise_wrapfail(teardown, "has second yield")
|
|
|
| if exception is not None:
|
| > raise exception
|
|
|
| venv\Lib\site-packages\pluggy\_callers.py:167:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| hook_name = 'pytest_pyfunc_call'
|
| hook_impls = [<HookImpl plugin_name='python', plugin=<module '_pytest.python' from 'D:\\a\\austin\\austin\\venv\\Lib\\site-packages\\_pytest\\python.py'>>]
|
| caller_kwargs = {'pyfuncitem': <Function test_fork_cpu_time_cpu_bound[austin-3.14]>}
|
| firstresult = True
|
|
|
| def _multicall(
|
| hook_name: str,
|
| hook_impls: Sequence[HookImpl],
|
| caller_kwargs: Mapping[str, object],
|
| firstresult: bool,
|
| ) -> object | list[object]:
|
| """Execute a call into multiple python functions/methods and return the
|
| result(s).
|
|
|
| ``caller_kwargs`` comes from HookCaller.__call__().
|
| """
|
| __tracebackhide__ = True
|
| results: list[object] = []
|
| exception = None
|
| try: # run impl and wrapper setup functions in a loop
|
| teardowns: list[Teardown] = []
|
| try:
|
| for hook_impl in reversed(hook_impls):
|
| try:
|
| args = [caller_kwargs[argname] for argname in hook_impl.argnames]
|
| except KeyError as e:
|
| # coverage bug - this is tested
|
| for argname in hook_impl.argnames: # pragma: no cover
|
| if argname not in caller_kwargs:
|
| raise HookCallError(
|
| f"hook call must provide argument {argname!r}"
|
| ) from e
|
|
|
| if hook_impl.hookwrapper:
|
| function_gen = run_old_style_hookwrapper(hook_impl, hook_name, args)
|
|
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
|
|
| elif hook_impl.wrapper:
|
| try:
|
| # If this cast is not valid, a type error is raised below,
|
| # which is the desired response.
|
| res = hook_impl.function(*args)
|
| function_gen = cast(Generator[None, object, object], res)
|
| next(function_gen) # first yield
|
| teardowns.append(function_gen)
|
| except StopIteration:
|
| _raise_wrapfail(function_gen, "did not yield")
|
| else:
|
| > res = hook_impl.function(*args)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| venv\Lib\site-packages\pluggy\_callers.py:121:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| pyfuncitem = <Function test_fork_cpu_time_cpu_bound[austin-3.14]>
|
|
|
| @hookimpl(trylast=True)
|
| def pytest_pyfunc_call(pyfuncitem: Function) -> object | None:
|
| testfunction = pyfuncitem.obj
|
| if is_async_function(testfunction):
|
| async_fail(pyfuncitem.nodeid)
|
| funcargs = pyfuncitem.funcargs
|
| testargs = {arg: funcargs[arg] for arg in pyfuncitem._fixtureinfo.argnames}
|
| > result = testfunction(**testargs)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| venv\Lib\site-packages\_pytest\python.py:166:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| py = '3.14', austin = Variant('austin')
|
|
|
| @allpythons()
|
| @variants
|
| def test_fork_cpu_time_cpu_bound(py, austin):
|
| > result = austin("-ci", "1ms", *python(py), target("target34.py"))
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| test\functional\test_fork.py:78:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = Variant('austin'), timeout = 60, convert = True, expect_fail = False
|
| args = ('-ci', '1ms', 'py', '-3.14', 'D:\\a\\austin\\austin\\test\\targets\\target34.py')
|
|
|
| def __call__(
|
| self,
|
| *args: str,
|
| timeout: int = 60,
|
| convert: bool = True,
|
| expect_fail: Union[bool, int] = False,
|
| ) -> CompletedProcess:
|
| if not self.path.is_file():
|
| if "PYTEST_CURRENT_TEST" in os.environ:
|
| pytest.skip(f"{self} not available")
|
| else:
|
| raise FileNotFoundError(f"Binary {self.path} not found for {self}")
|
|
|
| extra_args = ["-b"] if "-b, --binary" in self.help else []
|
|
|
| try:
|
| flags = 0
|
| if sys.platform == "win32":
|
| flags = CREATE_NEW_PROCESS_GROUP
|
|
|
| result = run(
|
| [str(self.path)] + extra_args + list(args),
|
| capture_output=True,
|
| timeout=timeout,
|
| creationflags=flags,
|
| )
|
| except Exception as exc:
|
| if (pid := getattr(exc, "pid", None)) is not None:
|
| print_logs(collect_logs(self.name, pid))
|
| raise
|
|
|
| > return self.prepare_result(result, expect_fail, convert)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| test\utils.py:322:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = Variant('austin')
|
| result = CompletedProcess(args=['src\\austin.exe', '-ci', '1ms', 'py', '-3.14', 'D:\\a\\austin\\austin\\test\\targets\\target34...m998.33 Hz\x1b[0m\r\n Error rate\x1b[0;30m . . . . . . . . \x1b[0m\x1b[1m0/2046\x1b[0m (\x1b[1m0.00%\x1b[0m)\r\n")
|
| expect_fail = False, convert = True
|
|
|
| def prepare_result(self, result, expect_fail, convert):
|
| if result.returncode in (-11, 139): # SIGSEGV
|
| print(bt(self.path, result.pid))
|
|
|
| # If we are writing to stdout, check if we need to convert the stream
|
| if result.stdout.startswith(b"MOJ"):
|
| if convert:
|
| try:
|
| result.samples, result.metadata = parse_mojo(result.stdout)
|
| except Exception as e:
|
| dump_mojo(result.stdout)
|
| > raise e
|
|
|
| test\utils.py:335:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = Variant('austin')
|
| result = CompletedProcess(args=['src\\austin.exe', '-ci', '1ms', 'py', '-3.14', 'D:\\a\\austin\\austin\\test\\targets\\target34...m998.33 Hz\x1b[0m\r\n Error rate\x1b[0;30m . . . . . . . . \x1b[0m\x1b[1m0/2046\x1b[0m (\x1b[1m0.00%\x1b[0m)\r\n")
|
| expect_fail = False, convert = True
|
|
|
| def prepare_result(self, result, expect_fail, convert):
|
| if result.returncode in (-11, 139): # SIGSEGV
|
| print(bt(self.path, result.pid))
|
|
|
| # If we are writing to stdout, check if we need to convert the stream
|
| if result.stdout.startswith(b"MOJ"):
|
| if convert:
|
| try:
|
| > result.samples, result.metadata = parse_mojo(result.stdout)
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
| test\utils.py:332:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| data = b'MOJ\x04\x01austin\x004.0.0\x00\x01interval\x001000\x00\x01mode\x00cpu\x00\x01python\x003.14.4\x00\x02\x8c[\x001210\x...46\x00\x01duration\x002049415\x00\x01sampling\x00354,743,1650\x00\x01saturation\x0022/2049\x00\x01errors\x000/2046\x00'
|
|
|
| def parse_mojo(data: bytes) -> Tuple[List[AustinSample], Dict[str, str]]:
|
| mojo = MojoStreamReader(BytesIO(data))
|
| > samples = [_ for _ in mojo if isinstance(_, AustinSample)]
|
| ^^^^
|
|
|
| test\utils.py:505:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <austin.format.mojo.MojoStreamReader object at 0x000001F9C2319D00>
|
|
|
| def __iter__(self) -> t.Iterator[AustinEvent]:
|
| """Iterate over the MOJO file."""
|
| > for e in self.parse():
|
| ^^^^^^^^^^^^
|
|
|
| venv\Lib\site-packages\austin\format\mojo.py:664:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <austin.format.mojo.MojoStreamReader object at 0x000001F9C2319D00>
|
|
|
| def parse(self) -> t.Iterator[MojoEvent]:
|
| """Parse the MOJO file.
|
|
|
| Produces a stream of events.
|
| """
|
| # Check the MOJO header
|
| if self.mojo_version is None:
|
| if self.read(3) != b"MOJ":
|
| raise ValueError("Not a MOJO stream")
|
|
|
| # Get the MOJO version
|
| self.mojo_version = self.read_int()
|
|
|
| # Store the header bytes
|
| self.header = bytes(self._last_bytes)
|
| self._last_bytes.clear()
|
|
|
| # Parse the MOJO events
|
| while True:
|
| > if (e := self.parse_event()) is None:
|
| ^^^^^^^^^^^^^^^^^^
|
|
|
| venv\Lib\site-packages\austin\format\mojo.py:653:
|
| _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
|
|
|
| self = <austin.format.mojo.MojoStreamReader object at 0x000001F9C2319D00>
|
|
|
| def parse_event(self) -> t.Optional[MojoEvent]:
|
| """Parse a single event."""
|
| try:
|
| (event_id,) = self.read()
|
| except ValueError:
|
| return None
|
|
|
| try:
|
| event = t.cast(dict, self.__handlers__)[event_id](self)
|
| object.__setattr__(event, "raw", bytes(self._last_bytes))
|
| self._last_bytes.clear()
|
| return event
|
| except KeyError as exc:
|
| > raise ValueError(
|
| f"Unhandled event: {event_id} (offset: {self._offset}, last read: {self._last_read})"
|
| ) from exc
|
| E ValueError: Unhandled event: 13 (offset: 238, last read: 1)
|
|
|
| venv\Lib\site-packages\austin\format\mojo.py:627: ValueError
|