Multitasking [sticky] - When and When Not to Multitask
Author |
Message |
bfeher
Site Admin
Joined: Mon Jun 08, 2009 4:50 pm Posts: 70
|
 Multitasking [sticky] - When and When Not to Multitask
Multitasking is when the robot performs multiple complex behaviors at the same time (simultaneously). If a robot performs behaviors step-by-step (sequentially) then it is not multitasking and should not be programmed with multiple tasks. Let’s look at few examples and determine whether or not multitasking should be used. A robot drives forward until the sonar sensor sees and object at 30 cm or less away, turns right and stops.A flowchart of this program would look like this: As you can see, this program is sequential because each step comes after the one above it. We DO NOT use multitasking in this example. Let’s look at another: A robot follows a line until it is 20 cm or less away from a basket and then drops a ball into the basket.A flowchart of this program would look like this: This program also runs from top-to bottom, but this time we have a sonar sensor and a light sensor that are checking their values and performing behaviors at the same time. Should we use multiple tasks here? No because we can combine the multiple behaviors into a single task like this: When multiple behaviors can be combined into a single task, we should always choose to do so instead of multitasking! When should one use multitasking then? Imagine a program that drives a robot around a room vacuuming up objects while avoiding people. The robot comes with an emergency stop button just incase the systems for avoiding people fail or the robot uprising begins and we need to deactivate our robot quickly (in the real world, kill switches are important for human safety). How would a flowchart for this program look like? It is difficult to make a linear step-by-step chart for this program because it is doing multiple things at the same time. Also, the emergency stop button needs constantly be checking while other behaviors are running because the robot must stop immediately when the button is pressed, no matter what else it may be doing at the time. We need multiple flow charts side-by-side: Driving flowchart:E-stop flowchart:The actual program would look something like this: Notice that even though behavior for picking up objects and the behavior for avoiding people are running at the same time, they can be combined into a single task. However, the emergency stop button requires a task on its own that runs in the background while the other behaviors are also running. Also please note the two “wait1Msec” commands that prevent each task from hogging the CPU. If a task doesn’t have any waiting in it, it may hog the CPU meaning that it will not let any other tasks run. It’s important to remember that task main is the main task of the program and when it finishes execution, all other tasks will be force-quit and the program will end. In our example, task main was always in a while(true) loop and didn’t end until task e_stop stopped all tasks. This very basic example shows a good use for when to use multitasking, however many very important and dangerous concepts have not been addressed. I encourage those who wish to know more to research Multitasking (multi threading) in C. Remember: 99% of all ROBOTC programs can be written without multiple tasks if you combine related behaviors!and 99.9% of all errors in programs that use multitasking are because of improper use of multitasking!!
_________________ Bence Feher
Undergraduate Intern - NREC, Robotics Academy ROBOTC - Testing/Documentation/Developer
Computer Science, Japanese, East Asian Studies University of Pittsburgh, Konan University 甲南大学
|
Wed Jun 22, 2011 1:16 pm |
|
 |
jbflot
Site Admin
Joined: Tue May 15, 2007 9:02 am Posts: 409
|
 Re: Multitasking [sticky] - When and When Not to Multitask
Nice post!
|
Thu Jun 23, 2011 2:08 pm |
|
 |
bluesaberist
Rookie
Joined: Sat Nov 22, 2008 8:06 pm Posts: 48
|
 Re: Multitasking [sticky] - When and When Not to Multitask
100% of all programs can be written without multiple tasks on a single core microcontroller, unless you consider any interrupt a different task, in which case 0% of ROBOT C programs can be written without multiple tasks, because the Robot C operating system is interrupt driven.
Any program can be written without using multiple task, it just a matter of whether it's worth the time and skill to do it.
|
Sat Aug 27, 2011 12:08 am |
|
 |
magicode
Moderator
Joined: Tue Sep 14, 2010 9:19 pm Posts: 496
|
 Re: Multitasking [sticky] - When and When Not to Multitask
In some programs, multitasking is definitely the more elegant solution. While writing that program without multitasking may be possible, and it may take skill, it's not necessarily the best way to go about it. Multitasking is a tool, and should be used in the proper circumstances. The problems arise when people use this tool in the improper circumstances.
_________________ sudo rm -rf /
|
Sat Aug 27, 2011 6:42 am |
|
 |
MauiJerry
Rookie
Joined: Sun Sep 18, 2011 3:54 am Posts: 2
|
 Re: Multitasking [sticky] - When and When Not to Multitask
Multi-tasking is a tricky issue. Usually it requires knowing about things like semaphores, locks, etc. RobotC Cortex seems to have a very very rudimentary multi-tasking basically StartTask StopTask and some priority/time slice functions. nothing to support/prevent contention on variables, sensors, motors, etc and no way to WaitForTaskToComplete() or is this documented elsewhere than http://www.robotc.net/support/vex/WebHelpCortex/ ?
|
Sun Sep 18, 2011 4:15 am |
|
 |
charsleysa
Rookie
Joined: Mon Jan 10, 2011 11:39 pm Posts: 16
|
 Re: Multitasking [sticky] - When and When Not to Multitask
A Reply for the poster above: Its actually not documented but they have some sort of support for semaphores, its really basic and requires you to do most of the checking, its basically just a struct which the firmwares puts information to, like which task owns it and if it is locked or not. Its new with 3.0, you will see it on the cortex platform under Semaphore in the sidebar. As for waiting for a task to complete, you can bypass that by using global variables, for instance a boolean that holds the status and you just create a while loop to keep checking. Example:
boolean Completed = false; StartTask(exampleTask); while (Completed == false) {};
BE AWARE: this will cause the task your running this code from to freeze until "exampleTask" has finished executing which can lead to problems if it gets stuck in some sort of infinite loop.
_________________Regards Stefan Andres Charsley charsleysa@gmail.com
|
Wed Sep 28, 2011 12:48 am |
|
 |
mightor
Site Admin
Joined: Wed Mar 05, 2008 8:14 am Posts: 3654 Location: Rotterdam, The Netherlands
|
 Re: Multitasking [sticky] - When and When Not to Multitask
Consider using these new functions in 3.x: - Xander
_________________| Professional Conduit of Reasonableness| (Title bestowed upon on the 8th day of November, 2013) | My Blog: I'd Rather Be Building Robots| ROBOTC 3rd Party Driver Suite: [ Project Page]
|
Thu Sep 29, 2011 2:17 pm |
|
 |
brokenrinker
Rookie
Joined: Sat Dec 17, 2011 9:27 pm Posts: 1
|
 Re: Multitasking [sticky] - When and When Not to Multitask
I'm new to robotC (or programming in general) and am having a hard time getting a handle on the idea of linear steps. I'm much more comfortable with PLC ladder logic and am trying to make robotC work in a similar fashion.
I've been trying to write a program that would, basically, turn on a motor and reverse it's direction at time intervals. While this is going on I want to use a limit switch to stop and start another motor.
I think I'm making this far more complicated than it needs to be. I've been playing around with task control etc but I don't even know what I don't know.
Can anybody suggest some ways I might be able to approach the problem stated above?
|
Sat Dec 17, 2011 9:36 pm |
|
 |
magicode
Moderator
Joined: Tue Sep 14, 2010 9:19 pm Posts: 496
|
 Re: Multitasking [sticky] - When and When Not to Multitask
Maybe this question should be in a separate thread. You could use boolean flags to make this work without multitasking, but multitasking might make it easier. How do you want the switch to control the second motor? Run it while the switch is pressed and stop when released? Or run when the switch is pressed and released, and stop when it's pressed and released again?
_________________ sudo rm -rf /
|
Sun Dec 18, 2011 12:32 am |
|
 |
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1523
|
 Re: Multitasking [sticky] - When and When Not to Multitask
From my point of view, there are two ways of doing multiple things at the same time. You can either use the "task" feature in RobotC. The task feature in RobotC is implementing preemptive multi-tasking which has a lot of gotcha's especially if you are accessing common resources in multiple tasks. Or you can do cooperative multi-tasking. The main idea of cooperative multi-tasking is to write a function for each task and make sure each of these functions do not block (i.e. you should never call any wait1Msec, wait10Msec etc or have any loops in the function). Whenever you need to wait for something to happen, remember where you are and return instead so another task can run. When your task is run again, retrieve the state where you were and continue. To explain it better, I always use the example of baking a pizza and doing laundry at the same time. First list out the steps for baking a pizza. Next, list out the steps for doing laundry. If you are smart, you are not going to stare at the oven while it is pre-heating or stare at the washing machine while it is washing your clothes. Instead, you leave and do something else and come back to check on it later. That's what multi-tasking is about. Imagine the above steps to bake a pizza or doing laundry are written as separate functions. If you call one function then the other, you are serializing the two tasks. One cannot start before the other is completed. However, if you structure your functions like the following, it will do both tasks simultaneously. Since these two tasks are actually running on the same thread, there is no resource contention problem or synchronization issue. In essence, your task main loop is the task scheduler. It calls the next task when the previous task is willingly giving up processing. And it is doing this over and over again until all the tasks are completed.
|
Sun Dec 18, 2011 3:33 am |
|
 |
magicode
Moderator
Joined: Tue Sep 14, 2010 9:19 pm Posts: 496
|
 Re: Multitasking [sticky] - When and When Not to Multitask
I am not familiar with how the multitasking is done internally in ROBOTC. Would the "cooperative multitasking" that you mentioned above actually execute faster than the method that ROBOTC offers, or would the function overhead make it execute slower? Perhaps I'll run some tests when I get my hand on a cortex again.
_________________ sudo rm -rf /
|
Sun Dec 18, 2011 10:27 am |
|
 |
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1523
|
 Re: Multitasking [sticky] - When and When Not to Multitask
It's not about faster or slower. It's about more controlled. In preemptive multi-tasking, the scheduler is on time slices. If a time slice is expiring, the task is suspended regardless of what it is in the middle of processing. I am sorry. I am not familiar with the Cortex so I will show an example of the NXT. For example, in joystickDriver.c. If the above code got preempted at the specified spot, autonomous will get started erronously when communication is lost for a split second because StopPgm would have been zero'd briefly. That's just one of the gotcha's you will hit when programming with preemptive multi-tasking (accessing a common resource in multiple tasks). In this case, the common resource is the joystickCopy structure. Regarding performance, cooperative multi-tasking puts the scheduling in your own hand. If you task mis-behaved (e.g. have a wait or a loop in your task), the other tasks are going to be starved (hence cooperative).
|
Sun Dec 18, 2011 10:56 am |
|
 |
magicode
Moderator
Joined: Tue Sep 14, 2010 9:19 pm Posts: 496
|
 Re: Multitasking [sticky] - When and When Not to Multitask
Couldn't you just use hogCPU() and releaseCPU() to make sure that your tasks aren't interrupted at critical moments?
_________________ sudo rm -rf /
|
Sun Dec 18, 2011 11:46 am |
|
 |
MHTS
Guru
Joined: Sun Nov 15, 2009 5:46 am Posts: 1523
|
 Re: Multitasking [sticky] - When and When Not to Multitask
Yes, but then you are assuming you are aware of where in the code you need to protect by critical section. Sometimes this may not be obvious and hence hard to find bugs.
|
Sun Dec 18, 2011 2:09 pm |
|
 |
williamholdin
Rookie
Joined: Fri Jun 24, 2016 2:23 am Posts: 1
|
 Re: Multitasking [sticky] - When and When Not to Multitask
Even if one instruction runs on a CPU at any given time, computer programs comprise a lot more than just atomic assembly instructions. So for example, writing to the console (or a file) means you have to have to lock to ensure it works like you want. Only one thread can lock the object at a time, and any contending threads are blocked until the lock is released. If more than one thread contends the lock, they are queued on a “ready queue” and granted the lock on a first-come, first-served basis. More about... Thread LockWilliam
|
Fri Jun 24, 2016 2:27 am |
|
|
Who is online |
Users browsing this forum: No registered users and 2 guests |
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot post attachments in this forum
|
|