Skip to content

Introduce new Component class - #705

Merged
NicolasFussberger merged 36 commits into
eclipse-score:mainfrom
etas-contrib:pin-split
Oct 22, 2026
Merged

NicolasFussberger merged 36 commits into
eclipse-score:mainfrom
etas-contrib:pin-split

Conversation

@danth

@danth danth commented Sep 28, 2026 •

Copy link
Copy Markdown
Member

Start, stop, force stop, and ready conditions are now implemented as strategies which plug in to a central Component class.

The only interaction between these classes is a tiny Handle struct, which identifies the child process to act upon.

Ideally, the handle will stay internal to the Component, and higher level classes such as ProcessGroupManager and the Graph will have no knowledge of the underlying process.

This new architecture should improve:

  • ProcessInfoNode having a mixture of process- and component-level code.
  • ProcessLauncher also having code for process termination.
  • Difficulty in adding new ready conditions and component types.

As a start, this pull request just introduces the new classes, and has them call the existing ProcessLauncher from its original location.

Once the new component class is ready, we can change the Graph to start using it in place of ProcessInfoNode. Currently it is unused outside of tests.

Finally, we will clean up by moving the old code into its new locations (rather than just calling it).


for (const IReadyCondition* ready_condition : ready_conditions_)
{
const osal::OsalReturnType result = ready_condition->wait(handle_.value());

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Currently we have one overall ready timeout for the component.

if we had multiple ready conditions, I think this would mean all ready condition must be fulfilled within the ready_timeout. So it would not be that each ready condition can take the full ready timeout.

This makes me think that it could make sense to move the timeout checking in the component. Same for the shutdown timeout

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we could pass a timeout into the ready condition when it is called (rather than storing it). Then on each iteration through the list the component could calculate the remaining time until the overall deadline.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually I think it would be nice to pass a struct/class like Go contexts which has both a deadline and a stop token.

Then the ready condition can stop either when the deadline expires or cancellation is requested.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Timeouts will be implemented in a separate pull request. :))

Comment thread score/launch_manager/src/daemon/src/process_group_manager/details/component.cpp Outdated
Comment thread score/launch_manager/src/daemon/src/process_group_manager/details/component.cpp Outdated

if (process.pid > 0)
{
if (kill(process.pid, SIGTERM) == 0)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we'll need to decide where the timeout monitoring takes place for the shutdown and the escalation to SIGKILL in case of timeout

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Timeouts will be implemented in a later pull request.

@danth danth changed the title Refactor ProcessInfoNode and ProcessLauncher Introduce new Component class Sep 30, 2026
danth added 20 commits October 16, 2026 16:31
Follow the naming conventions.
This is based on the diagram introduced in eclipse-score#736.
While `operator()` was slightly less code, the methods had to be
public for it to work.
For invalid handles, we should move to the terminated state immediately,
rather than waiting for a termination event.
This can be reintroduced once it is decided how a force stop is
triggered.

Link: https://github.com/eclipse-score/lifecycle/pull/705/changes#r4154237710
Just switch using if statements rather than a separate implementation
for each state.

This makes it more obvious how things work with concurrency.
@github-actions

Copy link
Copy Markdown
Contributor

Documentation preview for this pull request is available at:
pr-705: https://eclipse-score.github.io/lifecycle/pr-705/

lock.unlock();
for (const IReadyCondition& ready_condition : ready_conditions_)
{
if (!ready_condition.wait(stop_activation.get_token(), handle).has_value())

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The ready_condition gets a copy of the handle, so it will not actually observe if the pid was set to -1 if the process terminated inbetween. However, passing the actual reference to the handle from the state would lead to data race since there is no lock and oshandler thread also modifies it

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree. However, no ready conditions rely on the PID at the moment.

Maybe we can leave this as an open point for now, to avoid blocking the pull request?

If so, I'll create a separate issue to address this :))

Comment thread score/launch_manager/src/daemon/src/process_group_manager/details/component.cpp Outdated
Comment thread score/launch_manager/src/daemon/src/process_group_manager/details/component.cpp Outdated
return RequestState::kSuccess;
}

SCORE_LANGUAGE_FUTURECPP_UNREACHABLE_MESSAGE("If stop was not requested, then state must still be StartingState");

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this actually reachable for self-terminating processes where no stop was requested in tryHandleTermination?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When no stop is requested, the state is not changed. So, if the activate method is still running, then the state must still be starting. If the process terminates after it enters the ready state, activate has already returned so the assertion is not reached

if (self_terminating_ && status == 0)
{
return RequestState::kWaiting;
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How do we move from Starting->Ready for a self-terminating process that has ready condition ProcessState:Terminated?
Is there a ReadyCondition currently missing for this case?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, the ready condition is missing because we were waiting for #738. As a separate pull request we can adapt that code to implement the ready condition interface

@NicolasFussberger

Copy link
Copy Markdown
Contributor

This PR introduces new classes which are not yet used by the production code.
Not all functionality is implemented yet and it will continue in further PRs before it will be enabled in the production code.

This branch was successfully deployed

1 active deployment
workflow-approval — cd30deba Deployed Oct 20, 2026 by danth via Build and test arm64-qnx / approval #1633
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Status: Done

Development

Successfully merging this pull request may close these issues.

3 participants