Beispiel #1
0
int sbSimpleReachNavState(SBApiSimpleContext *context, 
		int desired, double timeout_sec)
{
	int res;
	SBHeliState state;
	double t0 = now();
	double t_lastprint = -2;

	static int transition[8*8] = {
	// to:  stop         idle	      takeoff         land         hover           cntrl           sink  raw     
			SB_NAV_STOP, SB_NAV_IDLE, SB_NAV_IDLE,             -1, SB_NAV_IDLE,    SB_NAV_IDLE,    -1,   SB_NAV_RAW,// from stop
			SB_NAV_STOP, SB_NAV_IDLE, SB_NAV_TAKEOFF,          -1, SB_NAV_TAKEOFF, SB_NAV_TAKEOFF, -1,   SB_NAV_STOP, // from idle
			SB_NAV_LAND, SB_NAV_LAND, SB_NAV_TAKEOFF, SB_NAV_LAND, SB_NAV_TAKEOFF, SB_NAV_TAKEOFF, -1,   SB_NAV_LAND,// from takeoff
			SB_NAV_LAND, SB_NAV_LAND, SB_NAV_LAND,    SB_NAV_LAND, SB_NAV_LAND,    SB_NAV_LAND,    -1,   SB_NAV_LAND,// from land
			SB_NAV_LAND, SB_NAV_LAND, SB_NAV_LAND,    SB_NAV_LAND, SB_NAV_HOVER,   SB_NAV_CTRLLED, -1,   SB_NAV_LAND,// from hover
			SB_NAV_LAND, SB_NAV_LAND, SB_NAV_LAND,    SB_NAV_LAND, SB_NAV_HOVER,   SB_NAV_CTRLLED, -1,   SB_NAV_LAND,// from ctrlled
			SB_NAV_LAND, SB_NAV_LAND, SB_NAV_LAND,    SB_NAV_LAND, SB_NAV_HOVER,   SB_NAV_CTRLLED, -1,   SB_NAV_LAND,// from sink
			SB_NAV_STOP, SB_NAV_STOP,          -1,    SB_NAV_LAND, SB_NAV_LAND,    SB_NAV_LAND,    -1,   SB_NAV_RAW  // from raw (no transition allowed)
	};

	switch (desired) {
		case SB_NAV_TAKEOFF:
		case SB_NAV_LAND:
			printf("sbSimpleReachNavState: Take-off and landing mode are transcient and cannot be used as target for sbSimpleReachNavState\n");
			return -1;
		case SB_NAV_SINK:
			printf("sbSimpleReachNavState: Sink mode is an error mode and cannot be used as target for sbSimpleReachNavState\n");
			return -1;
		default:
			break;
	}

	switch (context->commMode) {
		case SB_COM_CONTINUOUS:
			DEBUG(res = sbSimpleWaitState(context,&state,1.0));
			break;
		case SB_COM_ONREQUEST:
			sbLockCommunication(&context->control);
			DEBUG(res = sbRequestState(&context->control,SBS_MODES,&state));
			sbUnlockCommunication(&context->control);
			break;
		default:
			res = -1;
	}

	if (res) {
		printf("sbSimpleReachNavState: Could not receive initial state\n");
		return -1;
	}
	if (!(state.content & SBS_MODES)) {
		printf("sbSimpleReachNavState: initial state did not contains MODES\n");
		return -1;
	}
	if (desired == state.mode.navigation) {
		return 0;
	}

    if ((desired != SB_NAV_STOP) && (state.errorFlags)) {
		printf("sbSimpleReachNavState: refusing to switch mode while error flags are raised\n");
        sbErrorPrint(stdout,state.errorFlags);
        return -1;
    }

	while (state.mode.navigation != desired) {
		double t = now();
		int nextstate;
		switch (context->commMode) {
			case SB_COM_CONTINUOUS:
				DEBUG(res = sbSimpleWaitState(context,&state,1.0));
				break;
			case SB_COM_ONREQUEST:
				sbLockCommunication(&context->control);
				DEBUG(res = sbRequestState(&context->control,SBS_MODES,&state));
				sbUnlockCommunication(&context->control);
				break;
			default:
				res = -1;
		}
		if (res) {
			printf("sbSimpleReachNavState: failed to receive state\n");
			return -4;
		}
		nextstate = transition[state.mode.navigation*8+desired];
		// Testing the validity of the transition
		if (nextstate < 0) {
			printf("sbSimpleReachNavState: cannot reach desired state. Aborting\n");
			return -2;
		}
		// printf("sbSimpleReachNavState: next state = %d / current %d\n",nextstate, state.mode.navigation);
		if (t < t0) t += 86400;
		if (t > t0 + timeout_sec) {
			printf("sbSimpleReachNavState timed out. Aborting\n");
			return -2;
		}

		if (t - t_lastprint > 2) {
			printf("Current %s desired: %s next %s wait %s rem t %.3f\n",
					sbNavModeString(state.mode.navigation),
					sbNavModeString(desired),sbNavModeString(nextstate),
					sbNavModeString(waitmode(nextstate)),t0 + timeout_sec - t);
			t_lastprint = t;
		}

		// Requesting the transition
		sbLockCommunication(&context->control);
		res = sbSetNavMode(&context->control,nextstate);
		res = sbKeepAlive(&context->control);
		sbUnlockCommunication(&context->control);
		switch (res) {
			case 0:
				// Good, it works
				break;
			case SB_REPLY_TOO_EARLY:
				continue;
				break;
			default:
				printf("sbSetNavAndWait failed (%d) to set desired mode. Aborting\n",res);
		}

#ifdef LINUX
		usleep(100000);
#endif
#ifdef WIN32
		Sleep(100);
#endif
	}
	// At this stage, the mode is the desired mode.
	if (state.mode.navigation == SB_NAV_CTRLLED) {
		// Confirm the control mode when we reach the
		// controlled state
		sbLockCommunication(&context->control);
		res = sbConfigureControl(&context->control,
				context->rollCtrlMode, context->pitchCtrlMode, 
				context->yawCtrlMode, context->altCtrlMode);
		sbUnlockCommunication(&context->control);
	}

	return 0;
}
Beispiel #2
0
void sbStatePrint(FILE * fp, const SBHeliState *hs) 
{
	fprintf(fp,"Content: "); sbContentPrint(fp,hs->content);
	fprintf(fp,"\n");
    sbErrorPrint(fp,hs->errorFlags);
	if (TESTCONTENT(hs->content,SBS_MODES)) {
		fprintf(fp,"Modes:\n");
		fprintf(fp,"\tNavigation %s",sbNavModeString(hs->mode.navigation));
		fprintf(fp,"\tCommunication %s",sbCommModeString(hs->mode.communication));
		fprintf(fp,"\tObst. Avoid: %s\n",sbOAModeString(hs->mode.oavoid));
		fprintf(fp,"\tAxis: Roll %s",sbCtrlModeString(hs->mode.rollAxis));
		fprintf(fp,"\tPitch %s",sbCtrlModeString(hs->mode.pitchAxis));
		fprintf(fp,"\tYaw %s",sbCtrlModeString(hs->mode.yawAxis));
		fprintf(fp,"\tAlti. %s",sbCtrlModeString(hs->mode.altAxis));
		fprintf(fp,"\n");
	}
	if (TESTCONTENT(hs->content,SBS_TIMESTAMP)) {
		fprintf(fp,"Timestamp: %8ld\n",hs->timeStamp);
	}
	if (TESTCONTENT(hs->content,SBS_RPY)) {
		fprintf(fp,"RPY (deg): %+6.2f, %+6.2f, %+6.2f\n",R2D(hs->roll), R2D(hs->pitch), R2D(hs->yaw));
	}
	if (TESTCONTENT(hs->content,SBS_GYRO)) {
		fprintf(fp,"Gyro (deg/s): %+6.2f, %+6.2f, %+6.2f\n",R2D(hs->gyro[0]), R2D(hs->gyro[1]), R2D(hs->gyro[2]));
	}
	if (TESTCONTENT(hs->content,SBS_ACCEL)) {
		fprintf(fp,"Accel (m/s2): %+5.2f, %+5.2f, %+5.2f\n",hs->accel[0], hs->accel[1], hs->accel[2]);
	}
	if (TESTCONTENT(hs->content,SBS_MAGNETO)) {
		fprintf(fp,"Magneto: %+5.2f, %+5.2f, %+5.2f\n",hs->magneto[0], hs->magneto[1], hs->magneto[2]);
	}
	if (TESTCONTENT(hs->content,SBS_IMUTEMP)) {
		fprintf(fp,"IMU Temp (degC): %.2f\n",hs->imutemp);
	}
	if (TESTCONTENT(hs->content,SBS_ALTITUDE)) {
		fprintf(fp,"Z Range (m): %+4.2f Filtered (m): %.2f\n",
				hs->zrange, hs->zfiltered);
	}
	if (TESTCONTENT(hs->content,SBS_PRESSURE)) {
		fprintf(fp,"Pressure (?): %+6.2f\n",hs->pressure);
	}
	if (TESTCONTENT(hs->content,SBS_HRANGES)) {
		int i;
		fprintf(fp,"H ranges (m): ");
		for (i=0;i<4;i++) {
			if (hs->hranges[i]>65.5) {
				fprintf(fp,"inf "); 
			} else {
				fprintf(fp,"%4.2f ",hs->hranges[i]);
			}
		}
		printf("\n");
	}
	if (TESTCONTENT(hs->content,SBS_XY_REL)) {
		fprintf(fp,"XY Rel (m): %.2f, %.2f\n",hs->xrel, hs->yrel);
	}
	if (TESTCONTENT(hs->content,SBS_BATTERY)) {
		fprintf(fp,"Battery (V): %5.2f\n",hs->battery);
	}
	if (TESTCONTENT(hs->content,SBS_TIMEOUT)) {
		fprintf(fp,"Timeout (ms): WD %d CTRL %d \n",hs->watchdogTimeout,hs->controlTimeout);
	}
	if (TESTCONTENT(hs->content,SBS_CHANNELS)) {
		fprintf(fp,"Channels: %.3f %.3f %.3f %.3f\n\t%.3f %.3f %.3f %.3f \n",
				hs->rcChannel[0],hs->rcChannel[1],
				hs->rcChannel[2],hs->rcChannel[3],
				hs->rcChannel[4],hs->rcChannel[5],
				hs->rcChannel[6],hs->rcChannel[7]);
	}
	if (TESTCONTENT(hs->content,SBS_O_ATTITUDE)) {
		fprintf(fp,"Output Attitude: %f, %f, %f\n",hs->o_attitude[0], hs->o_attitude[1], hs->o_attitude[2]);
	}
	if (TESTCONTENT(hs->content,SBS_O_ALTITUDE)) {
		fprintf(fp,"Output Altitude: %f\n", hs->o_altitude);
	}
	if (TESTCONTENT(hs->content,SBS_O_TOL)) {
		fprintf(fp,"Output TOL: %04X\n",hs->o_tol);
	}
	if (TESTCONTENT(hs->content,SBS_O_XY)) {
		fprintf(fp,"Output XY: %f, %f\n",hs->o_xy[0], hs->o_xy[1]);
	}
	if (TESTCONTENT(hs->content,SBS_O_OAVOID)) {
		fprintf(fp,"Output OA XY: %f, %f\n", hs->o_oavoid[0], hs->o_oavoid[1]);
	}
	if (TESTCONTENT(hs->content,SBS_COAXSPEED)) {
        if (hs->coaxspeed.state & COAXSPEED_AVAILABLE) {
            if (hs->coaxspeed.state & COAXSPEED_VALID_MEASUREMENT) {
                fprintf(fp,"CoaxSpeed %02X: V %.3f %.3f L %3d%%\n",hs->coaxspeed.state,
                        hs->coaxspeed.vel_x, hs->coaxspeed.vel_y, hs->coaxspeed.light);
            } else {
                fprintf(fp,"CoaxSpeed %02X: V  invalid  L %3d%%\n",hs->coaxspeed.state, hs->coaxspeed.light);
            }
        } else {
            fprintf(fp,"CoaxSpeed %02X: not detected\n",hs->coaxspeed.state);
        }
	}
}