Changeset 22185
- Timestamp:
- 09/05/07 15:36:38 (15 months ago)
- Files:
-
- 1 modified
-
haiku/trunk/src/system/kernel/team.cpp (modified) (6 diffs)
Legend:
- Unmodified
- Added
- Removed
-
haiku/trunk/src/system/kernel/team.cpp
r22161 r22185 2412 2412 struct thread *thread = thread_get_current_thread(); 2413 2413 struct team *currentTeam = thread->team; 2414 struct process_group *group = NULL, *freeGroup = NULL;2415 2414 struct team *team; 2416 cpu_status state;2417 2415 team_id teamID = -1; 2418 status_t status = B_OK;2419 2420 // TODO: we might want to notify waiting wait_for_child() threads in case2421 // they wait for children of the former process group ID (see wait_test_4.cpp)2422 2416 2423 2417 if (groupID < 0) … … 2440 2434 return B_NOT_ALLOWED; 2441 2435 } 2442 2443 status = B_OK;2444 2436 } else { 2445 state = disable_interrupts(); 2446 GRAB_THREAD_LOCK(); 2437 InterruptsSpinLocker _(thread_spinlock); 2447 2438 2448 2439 thread = thread_get_thread_struct_locked(processID); … … 2450 2441 // the thread must be the team's main thread, as that 2451 2442 // determines its process ID 2452 if (thread != NULL && thread == thread->team->main_thread) { 2453 // check if the thread is in a child team of the calling team and 2454 // if it's already a process group leader and in the same session 2455 if (thread->team->parent != currentTeam 2456 || is_process_group_leader(thread->team) 2457 || thread->team->session_id != currentTeam->session_id) 2458 status = B_NOT_ALLOWED; 2459 else 2460 teamID = thread->team->id; 2461 } else 2462 status = B_BAD_THREAD_ID; 2463 2464 RELEASE_THREAD_LOCK(); 2465 restore_interrupts(state); 2466 } 2467 2468 if (status != B_OK) 2469 return status; 2443 if (thread == NULL && thread != thread->team->main_thread) 2444 return B_BAD_THREAD_ID; 2445 2446 // check if the thread is in a child team of the calling team and 2447 // if it's already a process group leader and in the same session 2448 if (thread->team->parent != currentTeam 2449 || is_process_group_leader(thread->team) 2450 || thread->team->session_id != currentTeam->session_id) { 2451 return B_NOT_ALLOWED; 2452 } 2453 2454 // TODO: According to the standard, the call is also supposed to fail 2455 // on a child, when the child already has executed exec*(). 2456 2457 teamID = thread->team->id; 2458 } 2470 2459 2471 2460 // if the group ID is not specified, a new group should be created … … 2473 2462 groupID = processID; 2474 2463 2464 struct process_group *group = NULL; 2475 2465 if (groupID == processID) { 2476 2466 // We need to create a new process group for this team … … 2480 2470 } 2481 2471 2482 state = disable_interrupts(); 2483 GRAB_TEAM_LOCK(); 2472 status_t status = B_OK; 2473 struct process_group *freeGroup = NULL; 2474 2475 InterruptsSpinLocker locker(team_spinlock); 2484 2476 2485 2477 team = team_get_team_struct_locked(teamID); 2486 2478 if (team != NULL) { 2487 2479 if (processID == groupID) { 2488 // we created a new process group, let us insert it into the team's session 2480 // we created a new process group, let us insert it into the team's 2481 // session 2489 2482 insert_group_into_session(team->group->session, group); 2490 2483 remove_team_from_group(team, &freeGroup); 2491 2484 insert_team_into_group(group, team); 2492 2485 } else { 2493 // check if this team can have the group ID; there must be one matching2494 // process ID in the team's session2495 2496 struct process_group * group =2486 // check if this team can have the group ID; there must be one 2487 // matching process ID in the team's session 2488 2489 struct process_group *targetGroup = 2497 2490 team_get_process_group_locked(team->group->session, groupID); 2498 if ( group) {2491 if (targetGroup != NULL) { 2499 2492 // we got a group, let's move the team there 2500 2493 remove_team_from_group(team, &freeGroup); 2501 insert_team_into_group( group, team);2494 insert_team_into_group(targetGroup, team); 2502 2495 } else 2503 2496 status = B_NOT_ALLOWED; … … 2506 2499 status = B_NOT_ALLOWED; 2507 2500 2508 RELEASE_TEAM_LOCK(); 2509 restore_interrupts(state); 2501 // Changing the process group might have changed the situation for a parent 2502 // waiting in wait_for_child(). Hence we notify it. 2503 if (status == B_OK) { 2504 team->parent->dead_children->condition_variable.NotifyAll(false); 2505 team->parent->stopped_children->condition_variable.NotifyAll(false); 2506 team->parent->continued_children->condition_variable.NotifyAll(false); 2507 } 2508 2509 locker.Unlock(); 2510 2510 2511 2511 if (status != B_OK && group != NULL) {
