3 #include <ardrone_api.h>
4 #include <ardrone_tool/ardrone_tool.h>
5 #include <ardrone_tool/ardrone_tool_configuration.h>
6 #include <ardrone_tool/Navdata/ardrone_navdata_client.h>
7 #include <ardrone_tool/Navdata/ardrone_general_navdata.h>
8 #include <utils/ardrone_gen_ids.h>
10 static MULTICONFIG_STATE configState;
11 static NAVDATA_REQUEST_STATE navdataState;
12 static int appSwitch = 0;
13 static int usrSwitch = 0;
14 static int sesSwitch = 0;
15 static int navdataNeeded = 0;
16 static int droneSupportsMulticonfig = 0;
18 #define __MULTICONFIGURATION_MIN_VERSION_MAJOR__ (1U)
19 #define __MULTICONFIGURATION_MIN_VERSION_MINOR__ (6U)
20 #define __MULTICONFIGURATION_MIN_VERSION_REVISION__ (0U)
21 #define __MULTICONFIGURATION_MIN_VERSION__ ((__MULTICONFIGURATION_MIN_VERSION_MAJOR__ << 16) | (__MULTICONFIGURATION_MIN_VERSION_MINOR__ << 8) | (__MULTICONFIGURATION_MIN_VERSION_REVISION__))
22 static inline int versionSupportsMulticonfiguration (const char *currentString)
24 uint32_t currentMajor = 0, currentMinor = 0, currentRevision = 0;
25 uint32_t currentVersion;
26 sscanf (currentString, "%d.%d.%d", ¤tMajor, ¤tMinor, ¤tRevision);
27 currentVersion = ((currentMajor << 16) | (currentMinor << 8) | (currentRevision));
28 return currentVersion >= __MULTICONFIGURATION_MIN_VERSION__;
32 #define _GENERAL_NAVDATA_DEBUG (0)
33 #define _GENERAL_NAVDATA_DEBUG_PREFIX "General Navdata : "
34 #if _GENERAL_NAVDATA_DEBUG
35 #define PRINTDBG(...) \
38 printf ("[%d] %s", __LINE__, _GENERAL_NAVDATA_DEBUG_PREFIX);\
39 printf (__VA_ARGS__); \
45 static void switchToSession(void)
47 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (session_id, ses_id, NULL);
50 static void switchToUser(void)
52 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (profile_id, usr_id, NULL);
55 static void switchToApplication(void)
57 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (application_id , app_id, NULL);
60 void configurationCallback (int res)
62 PRINTDBG ("Config callback called with result %d\n", res);
65 PRINTDBG ("State : %d\n", configState);
68 case MULTICONFIG_IN_PROGRESS_VERSION: // got config version
69 PRINTDBG ("Got config file\n");
70 configState = MULTICONFIG_GOT_DRONE_VERSION;
72 case MULTICONFIG_IN_PROGRESS_LIST: // got multiconfig ids
73 PRINTDBG ("Got ids list\n");
74 configState = MULTICONFIG_GOT_IDS_LIST;
76 case MULTICONFIG_IN_PROGRESS_IDS:
77 PRINTDBG ("Got current ids\n");
78 configState = MULTICONFIG_GOT_CURRENT_IDS;
80 case MULTICONFIG_IDLE:
81 case MULTICONFIG_GOT_IDS_LIST:
82 case MULTICONFIG_GOT_DRONE_VERSION:
83 case MULTICONFIG_GOT_CURRENT_IDS:
84 case MULTICONFIG_NEEDED:
85 case MULTICONFIG_REQUEST_NAVDATA:
90 PRINTDBG ("End of config callback call\n");
93 void navdataCallback (int res)
95 PRINTDBG ("Navdata callback called with result %d\n", res);
98 PRINTDBG ("State : %d\n", navdataState);
101 case NAVDATA_REQUEST_IN_PROGRESS: // Navdata request got acknowledged by the AR.Drone
102 navdataState = NAVDATA_REQUEST_IDLE;
104 case NAVDATA_REQUEST_IDLE:
105 case NAVDATA_REQUEST_NEEDED:
110 PRINTDBG ("End of navdata callback call\n");
113 C_RESULT ardrone_general_navdata_init( void* data )
115 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (session_id, "-all", NULL);
117 navdataState = NAVDATA_REQUEST_IDLE;
118 configState = MULTICONFIG_NEEDED;
127 C_RESULT ardrone_general_navdata_process( const navdata_unpacked_t* const pnd )
129 navdata_mode_t current_navdata_state = NAVDATA_BOOTSTRAP;
131 /* Makes sure the navdata stream will be resumed if the drone is disconnected and reconnected.
132 * Allows changing the drone battery during debugging sessions. */
133 if( ardrone_get_mask_from_state(pnd->ardrone_state, ARDRONE_NAVDATA_BOOTSTRAP) )
135 current_navdata_state = NAVDATA_BOOTSTRAP;
139 current_navdata_state = (ardrone_get_mask_from_state(pnd->ardrone_state, ARDRONE_NAVDATA_DEMO_MASK)) ? NAVDATA_DEMO : NAVDATA_FULL ;
142 if (current_navdata_state == NAVDATA_BOOTSTRAP && configState == MULTICONFIG_IDLE && navdataState == NAVDATA_REQUEST_IDLE)
144 navdataState = NAVDATA_REQUEST_NEEDED;
147 /* Multiconfig settings */
148 int configIndex, userNeedInit, appNeedInit;
149 userNeedInit = 0; appNeedInit = 0;
152 case MULTICONFIG_GOT_DRONE_VERSION:
153 PRINTDBG ("Checking drone version ...\n");
154 // Check if drone version is >= 1.6
155 if (versionSupportsMulticonfiguration (ardrone_control_config.num_version_soft))
157 PRINTDBG ("Drone supports multiconfig\n");
158 configState = MULTICONFIG_IN_PROGRESS_LIST;
159 ARDRONE_TOOL_CUSTOM_CONFIGURATION_GET (configurationCallback);
160 droneSupportsMulticonfig = 1;
164 PRINTDBG ("Drone does not support multiconfig\n");
165 // Drone does not support multiconfig ... don't call init functions because we don't want to mess up things in default config
166 configState = MULTICONFIG_REQUEST_NAVDATA;
169 case MULTICONFIG_GOT_IDS_LIST:
170 // At this point, we're sure that the AR.Drone supports multiconfiguration, so we'll wheck if our ids exists, and send them.
171 PRINTDBG ("Got AR.Drone ID list. Switch->%d,%d,%d. ND->%d\n", sesSwitch, usrSwitch, appSwitch, navdataNeeded);
174 switchToSession(); // Go to session ...
179 if (0 != strcmp(ardrone_control_config_default.application_id, app_id)) // Check for application only if we're not asking for the default one
182 for (configIndex = 0; configIndex < available_configurations[CAT_APPLI].nb_configurations; configIndex++) // Check all existing app_ids
184 PRINTDBG ("Checking application %s (desc : %s)\n", available_configurations[CAT_APPLI].list[configIndex].id,
185 available_configurations[CAT_APPLI].list[configIndex].description);
186 if (0 == strcmp(available_configurations[CAT_APPLI].list[configIndex].id, app_id))
188 PRINTDBG ("Found our application ... should not init\n");
193 switchToApplication();
197 PRINTDBG ("We're requesting default application (%s), do nothing.\n", app_id);
203 if (0 != strcmp(ardrone_control_config_default.profile_id, usr_id)) // Check for user only if we're not asking for the default one
206 for (configIndex = 0; configIndex < available_configurations[CAT_USER].nb_configurations; configIndex++) // Check all existing user_ids
208 PRINTDBG ("Checking user %s (desc : %s)\n", available_configurations[CAT_USER].list[configIndex].id,
209 available_configurations[CAT_USER].list[configIndex].description);
210 if (0 == strcmp(available_configurations[CAT_USER].list[configIndex].id, usr_id))
212 PRINTDBG ("Found our user ... should not init\n");
221 PRINTDBG ("We're requesting default user (%s), do nothing.\n", usr_id);
225 if (1 == appNeedInit)
227 // Send application defined default values
228 ardrone_tool_send_application_default();
229 PRINTDBG ("Creating app. profile on AR.Drone\n");
230 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (application_desc, app_name, NULL);
232 if (1 == userNeedInit)
234 // Send user defined default values
235 ardrone_tool_send_user_default();
236 PRINTDBG ("Creating usr. profile on AR.Drone\n");
237 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (profile_desc, usr_name, NULL);
241 if (0 != strcmp(ardrone_control_config_default.session_id, ses_id)) // Send session info only if session is not the default one
243 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (session_desc, ses_name, NULL);
244 // Send session specific default values
245 ardrone_tool_send_session_default();
249 PRINTDBG ("We're requesting default session (%s), do nothing.\n", ses_id);
252 configState = MULTICONFIG_IN_PROGRESS_IDS;
253 ARDRONE_TOOL_CONFIGURATION_GET (configurationCallback);
255 case MULTICONFIG_GOT_CURRENT_IDS:
256 if (0 != strcmp(ardrone_control_config.session_id, ses_id) ||
257 0 != strcmp(ardrone_control_config.profile_id, usr_id) ||
258 0 != strcmp(ardrone_control_config.application_id, app_id))
260 configState = MULTICONFIG_GOT_DRONE_VERSION; // We failed at setting up the application ids ... restart (but assume that drone supports multiconfig as we already checked)
262 else if (1 == navdataNeeded)
264 configState = MULTICONFIG_REQUEST_NAVDATA;
268 configState = MULTICONFIG_IDLE;
271 case MULTICONFIG_NEEDED:
272 PRINTDBG ("Need to check multiconfig ... request config file\n");
273 // Get config file for reset
274 configState = MULTICONFIG_IN_PROGRESS_VERSION;
275 ARDRONE_TOOL_CONFIGURATION_GET (configurationCallback);
277 case MULTICONFIG_REQUEST_NAVDATA:
278 PRINTDBG ("Send application navdata demo/options\n");
279 // Send application navdata demo/options to start navdatas from AR.Drone
280 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (navdata_demo, &ardrone_application_default_config.navdata_demo, NULL);
281 if (TRUE == ardrone_application_default_config.navdata_demo)
282 { // Send navdata options only for navdata demo mode
283 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (navdata_options, &ardrone_application_default_config.navdata_options, NULL);
285 configState = MULTICONFIG_IDLE;
287 case MULTICONFIG_IDLE:
288 case MULTICONFIG_IN_PROGRESS_LIST:
289 case MULTICONFIG_IN_PROGRESS_VERSION:
290 case MULTICONFIG_IN_PROGRESS_IDS:
295 /* Navdata request settings */
296 switch (navdataState)
298 case NAVDATA_REQUEST_NEEDED:
299 PRINTDBG ("Resetting navdatas to %s\n", (0 == ardrone_application_default_config.navdata_demo) ? "full" : "demo");
300 navdataState = NAVDATA_REQUEST_IN_PROGRESS;
301 switchToSession(); // Resend session id when reconnecting.
302 ARDRONE_TOOL_CONFIGURATION_ADDEVENT(navdata_demo, &ardrone_application_default_config.navdata_demo, NULL);
303 if (TRUE == ardrone_application_default_config.navdata_demo)
304 { // Send navdata options only for navdata demo mode
305 ARDRONE_TOOL_CONFIGURATION_ADDEVENT (navdata_options, &ardrone_application_default_config.navdata_options, navdataCallback);
308 case NAVDATA_REQUEST_IN_PROGRESS:
309 case NAVDATA_REQUEST_IDLE:
317 C_RESULT ardrone_general_navdata_release( void )
322 /* User switch/list functions */
326 void ardrone_refresh_user_list(void)
328 if (1 == droneSupportsMulticonfig)
334 configState = MULTICONFIG_GOT_DRONE_VERSION;
338 void ardrone_switch_to_user(const char *new_user)
340 if (1 == droneSupportsMulticonfig)
342 ardrone_gen_usrid (new_user, usr_id, usr_name, USER_NAME_SIZE);
347 configState = MULTICONFIG_GOT_DRONE_VERSION;
351 void ardrone_switch_to_user_id(const char *new_user_id)
353 if (1 == droneSupportsMulticonfig)
355 // We assume that the userlist is up to date
358 for (configIndex = 0; configIndex < available_configurations[CAT_USER].nb_configurations; configIndex++) // Check all existing user_ids
360 if (0 == strcmp(available_configurations[CAT_USER].list[configIndex].id, new_user_id))
369 strncpy (usr_id, new_user_id, MULTICONFIG_ID_SIZE);
374 configState = MULTICONFIG_GOT_DRONE_VERSION;
379 ardrone_users_t *ardrone_get_user_list(void)
381 if (0 == droneSupportsMulticonfig)
385 ardrone_users_t *retVal = vp_os_malloc (sizeof (ardrone_users_t));
390 // Assume that userlist is up to date
391 int validUserCount = 0; // User whose descriptions start with a dot ('.') are hidden users that may not be shown to the application user (e.g. default user for each iPhone, or user specific to a control mode
393 for (configIndex = 0; configIndex < available_configurations[CAT_USER].nb_configurations; configIndex++) // Check all existing user_ids
395 if ('.' != available_configurations[CAT_USER].list[configIndex].description[0]) // Not an hidden user
398 retVal->userList = vp_os_realloc (retVal->userList, validUserCount * sizeof (ardrone_user_t));
399 if (NULL == retVal->userList)
404 strncpy (retVal->userList[validUserCount-1].ident, available_configurations[CAT_USER].list[configIndex].id, MULTICONFIG_ID_SIZE);
405 strncpy (retVal->userList[validUserCount-1].description, available_configurations[CAT_USER].list[configIndex].description, USER_NAME_SIZE);
408 retVal->userCount = validUserCount;
412 void ardrone_free_user_list (ardrone_users_t **users)
416 if (NULL != (*users)->userList)
418 vp_os_free ((*users)->userList);