Tasks based programming questions

So I feel like our teams teleop code is in a pretty good place as of last night, and we’re getting started with autonomous (and the kinect :D). But I’m also a bit curious if I should consider shuffling some routines into tasks.

Here’s my current teleop code:


void TeleopPeriodic(void)
{
    // increment the number of teleop periodic loops completed
    m_telePeriodicLoops++;
    
    if (!BUTTON_CAMERA_ALIGN_SHOT_BUTTON())
    {
        anglesComputed = false;
        myRobot.TankDrive(stickLeftDrive,stickRightDrive);
        //myRobot.SetSafetyEnabled(true);
        myRobot.SetSafetyEnabled(false);
        testCount = 0;
    }
    CameraInitialize();
    AxisCamera &camera = AxisCamera::GetInstance("10.24.74.11");
    
    
    ManageAppendages();
    ManageElevator();
    ManageCatapult();
        
    if (camera.IsFreshImage())
    {
        ColorImage *colorImage = new ColorImage(IMAQ_IMAGE_HSL);
        camera.GetImage(colorImage);
        if (BUTTON_CAMERA_ALIGN_SHOT_BUTTON() && (anglesComputed == false))
        {
            DetermineTargetPosition(colorImage);
        }
        delete colorImage;
    }
}

void TeleopContinuous(void)
{
    if ((BUTTON_CAMERA_ALIGN_SHOT_BUTTON()) &&
    (anglesComputed == true))
    {
        RotateToTarget();
    }
}


My other question is do any of the WPILib constructs, like Jaguar, Joystick, Gyro, etc play nice when shared between tasks, or do I need to set things up with semaphores and protect them (semaphoreDriverStick.get) OR will the inards of the WPILib choke if I try to use these attributes outside of the main task (implying that I will need to get values and put them into a seperate variable so I can protect them)?

Unrelated question: How often is periodic? Is it called at a set rate, or is it only when control packets are recieved from the DS (which would really be semi-periodic)?

Thanks

You can look at the WPILib source code to answer most of your questions. So far we found almost no scenario that we must use tasks (with only one exception: vision targeting). Even with vision targeting, it is arguable if we need a separate task. The reason we use a separate task for vision targeting is because we did a performance test on the various image filtering functions and found that total time it took to process an image is about 150-200 msec. We do not want to call into vision processing and have the main robot task hang for 200 msec. The worst case could be worse if your filter parameters resulted in generating a lot of false positive particles. Having said that, we could “yield” to process other robot subsystems after each filtering step. That could be acceptable. But the longest step could still take up tens of msecs so in the interest of having a “responsive” robot, we opt to use task for vision processing. By limiting the use of tasks, we would avoid all the pitfalls with multi-tasking programming on sharing resources. If you are not fluent with multi-tasking programming, you could have weird bugs that are hard to debug.

According to the WPILib source code on IterativeRobot:

/*
 * The default period for the periodic function calls (seconds)
 * Setting the period to 0.0 will cause the periodic functions to follow
 * the Driver Station packet rate of about 50Hz.
 */
static const double kDefaultPeriod = 0.0;

It’s event driven. TeleOp is called each time a packet is received. The packets are supposed to be transmitted at ~20ms.
*
*