Since Main and Motion run as separate processes, they could potentially try to access the same motion command at the same time, leading to unpredictable behavior. The MotionManager enforces a set of locks to serialize access to the MotionCommands. Although you could call checkoutMotion() and checkinMotion() directly, it is instead recommended to use MMAccessor to automatically handle casting and checkin for you.
The other problem is that we are sharing the memory holding MotionCommands between processes. MotionManager will do the necessary magic behind the scenes to distribute new MotionCommands to all the involved processes (currently just Main and Motion)
You can create and add a new motion in one line:
If you want to do some more initializations not handled by the MotionCommand's constructor (the arg1, arg2, ... params) then you would want to do something like the following:
|
Public Types |
|
typedef MotionManagerMsg::MC_ID | MC_ID |
| | use this type when referring to the ID numbers that MotionManager hands out
|
Public Member Functions |
|
| MotionManager () |
| | Constructor, sets all the outputs to 0.
|
|
void | InitAccess (OSubject *subj) |
| | LOCKS MotionManager Everyone who is planning to use the MotionManager needs to call this before they access it or suffer a horrible fate
|
|
void | receivedMsg (const ONotifyEvent &event) |
| | LOCKS MotionManager This gets called by an OObject when it receives a message from one of the other OObject's MotionManagerComm Subject
|
|
void | RemoveAccess () |
| | needed in order to dereference shared memory regions before shutting down
|
|
void | processMsg (RCRegion *region) |
| | LOCKS MotionManager This gets called by receivedMsg when under Aperios, or directly if you already have an RCRegion
|
|
| ~MotionManager () |
| | destructor
|
|
|
void | setOutput (const MotionCommand *caller, unsigned int output, const OutputCmd &cmd) |
| | LOCKS MotionManager Requests a value be set for the specified output, copies cmd across frames
|
|
void | setOutput (const MotionCommand *caller, unsigned int output, const OutputCmd &cmd, unsigned int frame) |
| | LOCKS MotionManager Requests a value be set for the specified output in the specified frame
|
|
void | setOutput (const MotionCommand *caller, unsigned int output, const OutputCmd cmd[NumFrames]) |
| | LOCKS MotionManager Requests a value be set for the specified output across frames
|
|
void | setOutput (const MotionCommand *caller, unsigned int output, const OutputPID &pid) |
| | LOCKS MotionManager Requests a PID be set for the specified output, notice that this might be overruled by a higher priority motion
|
|
void | setOutput (const MotionCommand *caller, unsigned int output, const OutputCmd &cmd, const OutputPID &pid) |
| | LOCKS MotionManager Requests a value and PID be set for the specified output
|
|
void | setOutput (const MotionCommand *caller, unsigned int output, const OutputCmd cmd[NumFrames], const OutputPID &pid) |
| | LOCKS MotionManager Requests a value and PID be set for the specified output
|
|
const OutputCmd & | getOutputCmd (unsigned int output) const |
| | Returns the value of the output last sent to the OS. Note that this will differ from the sensed value in state, even when staying still. There is no corresponding getOutputPID because this value *will* duplicate the value in state.
|
|
void | setPriority (MC_ID mcid, float p) |
| | sets the priority level of a MotionCommand, symbolic values are available to give some guidelines -- see kIgnoredPriority through kEmergencyPriority
|
|
float | getPriority (MC_ID mcid) const |
| | returns priority level of a MotionCommand, symbolic values are available to give some guidelines -- see kIgnoredPriority through kEmergencyPriority
|
|
|
MC_ID | begin () const |
| | returns the MC_ID of the first MotionCommand
|
|
MC_ID | next (MC_ID cur) const |
| | returns the MC_ID of MotionCommand following the one that is passed
|
|
MC_ID | end () const |
| | returns the MC_ID of the one-past-the-end MotionCommand (like the STL)
|
|
unsigned int | size () const |
| | returns the number of MotionCommands being managed
|
|
You can have one MC check out and modify another, but make sure the other MC doesn't call setOutput()
|
|
MotionCommand * | checkoutMotion (MC_ID mcid, bool block=true) |
| | locks the command and possibly performs RTTI conversion; supports recursive calls
|
|
void | checkinMotion (MC_ID mcid) |
| | marks a MotionCommand as unused
|
|
MotionCommand * | peekMotion (MC_ID mcid) |
| | allows access to a MotionCommand without checking it out; warning never call a function based on this, only access member fields through it
|
|
unsigned int | checkoutLevel (MC_ID mcid) |
| | returns the number of times mcid has been checked out minus the times it's been checked in
|
|
bool | isOwner (MC_ID mcid) |
| | locks the command and possibly performs RTTI conversion; supports recursive calls
|
|
|
MC_ID | addPrunableMotion (const SharedObjectBase &sm, float priority=kStdPriority) |
| | LOCKS MotionManager adds a new motion (wrapped in a SharedObject) and marks that it should be automatically deleted when the MotionCommand::isAlive() returns false.
|
|
MC_ID | addPersistentMotion (const SharedObjectBase &sm, float priority=kStdPriority) |
| | LOCKS MotionManager adds a new motion (wrapped in a SharedObject) and marks that it should not be deleted, until removeMotion(MC_ID mcid) is called.
|
|
void | removeMotion (MC_ID mcid) |
| | LOCKS MotionManager removes the specified MotionCommand
|
|
|
void | lock () |
| | gets an exclusive lock on MotionManager - functions marked LOCKS MotionManager will cause (and require) this to happen automatically
|
|
bool | trylock () |
| | tries to get a lock without blocking
|
|
void | unlock () |
| | releases a lock on the motion manager
|
|
| void | getOutputs (float outputs[][NumOutputs]) |
| | LOCKS MotionManager called by MotionObject to fill in the output values for the next NumFrames frames (only MotoObj should call this...)
|
|
void | updateWorldState () |
| | call this when you want MotionManager to set the WorldState to reflect what things should be for unsensed outputs (LEDs, ears) (only MotoObj should be calling this...)
|
| bool | updatePIDs (OPrimitiveID primIDs[NumOutputs]) |
| | call this when you want MotionManager to update modified PID values, returns true if changes made (only MotoObj should be calling this...), see PIDMC for general PID documentation
|
Static Public Member Functions |
|
static void | setTranslator (EventTranslator *et) |
| | sets etrans, should be called before any events can be sent
|
Static Public Attributes |
| static const unsigned int | MAX_ACCESS = 2 |
| | This is the number of processes which will be accessing the MotionManager.
|
|
static const unsigned int | MAX_MOTIONS = 64 |
| | This is the maximum number of Motions which can be managed, can probably be increased reasonably without trouble.
|
|
static const MC_ID | invalid_MC_ID = MotionManagerMsg::invalid_MC_ID |
| | for errors and undefined stuff
|
|
Just to give you some guidelines for what values to use for different priority levels, but you can pick any value you like (that's why they are floats)
|
|
static const float | kIgnoredPriority = -1 |
| | won't be expressed, handy if you want to temporarily pause something
|
|
static const float | kBackgroundPriority = 0 |
| | will only be expressed if *nothing* else is using that joint
|
|
static const float | kLowPriority = 5 |
| | for stuff that's not background but lower than standard
|
|
static const float | kStdPriority = 10 |
| | for every-day commands
|
|
static const float | kHighPriority = 50 |
| | for stuff that should override standard stuff
|
|
static const float | kEmergencyPriority = 100 |
| | for really important stuff, such as the emergency stop
|
Protected Types |
|
typedef unsigned short | accID_t |
| | type to use to refer to accessors of MotionManager (or its locks)
|
typedef ListMemBuf< OutputState,
MAX_MOTIONS > | cmdstatelist_t |
| | shorthand for a list of OutputState's
|
Protected Member Functions |
| MC_ID | doAddMotion (const SharedObjectBase &sm, bool autoprune, float priority) |
| | does the actual work of adding a motion
|
|
MotionCommand * | convertMotion (MC_ID mc) |
| | sets up a motion command to be accessed by the current process
|
| void | setPID (unsigned int j, const float p[3]) |
| | LOCKS MotionManager, called internally to do the work of setting the PID... you probably want to call setOutput with an OutputPID argument, not this...
|
|
void | func_begin () |
| | called at the begining of many functions to lock MotionManager
|
|
void | func_end () |
| | called at the end of a function which called func_begin() to release it
|
|
template<class T> |
| T | func_end (T val) |
| | same as func_end(), except passes return value through
|
|
MC_ID | skip_ahead (MC_ID mcid) const |
| | during iteration, skips over motioncommands which are still in transit from on OObject to another
|
|
MC_ID | pop_free () |
| | pulls an entry from cmdlist's free section and returns its index
|
|
void | push_free (MC_ID a) |
| | puts an entry back into cmdlist's free section
|
Static Protected Member Functions |
|
static int | getAccID () |
Protected Attributes |
|
ListMemBuf< PIDUpdate, NumPIDJoints > | pidchanges |
| | stores PID updates, up to one per joint (if same is set more than once, it's just overwrites previous update)
|
ListMemBuf< CommandEntry,
MAX_MOTIONS, MC_ID > | cmdlist |
| | the list where MotionCommands are stored, remember, we're in a shared memory region with different base addresses - no pointers!
|
|
MC_ID | cur_cmd |
| | MC_ID of the MotionCommand currently being updated by getOutputs(), or NULL if not in getOutputs. This is used by the setOutput()'s to tell which MotionCommand is calling.
|
|
MutexLock< MAX_ACCESS > | MMlock |
| | The main lock for the class.
|
|
cmdstatelist_t | cmdstates [NumOutputs] |
| | requested positions by each of the MC's for each of the outputs
|
|
float | cmdSums [NumOutputs] |
| | Holds the final values for the outputs of the last frame generated.
|
|
OutputCmd | cmds [NumOutputs] |
| | Holds the weighted values and total weight for the outputs of the last frame.
|
|
accID_t | numAcc |
| | The number of accessors who have registered with InitAccess().
|
|
OSubject * | subjs [MAX_ACCESS] |
| | The OSubject for each process (accessor) on which it should be broadcast when a command is added.
|
Static Protected Attributes |
|
static int | _MMaccID [ProcessID::NumProcesses] |
| | Stores the accessor id assigned in InitAccess() for each process.
|
|
static EventTranslator * | etrans = NULL |
| | EventTranslator for sending events to Main -- each process will set the correct value for calls within that process.
|
Private Member Functions |
|
| MotionManager (const MotionManager &) |
| | this shouldn't be called...
|
|
MotionManager & | operator= (const MotionManager &) |
| | this shouldn't be called...
|
Classes |
| struct | CommandEntry |
| | All the information we need to maintain about a MotionCommand. More...
|
| class | OutputState |
| | holds the full requested value of an output More...
|
| struct | PIDUpdate |
| | used to request pids for a given joint More...
|