コード例 #1
0
ファイル: dwgpsnmea.c プロジェクト: TomWSmith/direwolf
int main (int argc, char *argv[])
{

	struct misc_config_s config;
	dwgps_info_t info;


	memset (&config, 0, sizeof(config));
	strlcpy (config.gpsnmea_port, "COM22", sizeof(config.gpsnmea_port));

	dwgps_init (&config, 3);

	while (1) {
	  dwfix_t fix;

	  fix = dwgps_read (&info)
;
	  text_color_set (DW_COLOR_INFO);
	  switch (fix) {
	    case DWFIX_2D:
	    case DWFIX_3D:
	      dw_printf ("%.6f  %.6f", info.dlat, info.dlon);
	      dw_printf ("  %.1f knots  %.0f degrees", info.speed_knots, info.track);
	      if (fix==3) dw_printf ("  altitude = %.1f meters", info.altitude);
	      dw_printf ("\n");
	      break;
	    case DWFIX_NOT_SEEN:
	    case DWFIX_NO_FIX:
	      dw_printf ("Location currently not available.\n");
	      break;
	    case DWFIX_NOT_INIT:
	      dw_printf ("GPS Init failed.\n");
	      exit (1);
	    case DWFIX_ERROR:
	    default:
	      dw_printf ("ERROR getting GPS information.\n");
	      break;
	  }
	  SLEEP_SEC (3);
	}
コード例 #2
0
ファイル: digipeater.c プロジェクト: TomWSmith/direwolf
int main (int argc, char *argv[])
{
	int e;
	failed = 0;
	char message[256];

	dedupe_init (4);

/* 
 * Compile the patterns. 
 */
	e = regcomp (&alias_re, "^WIDE[4-7]-[1-7]|CITYD$", REG_EXTENDED|REG_NOSUB);
	if (e != 0) {
	  regerror (e, &alias_re, message, sizeof(message));
	  text_color_set(DW_COLOR_ERROR);
	  dw_printf ("\n%s\n\n", message);
	  exit (1);
	}

	e = regcomp (&wide_re, "^WIDE[1-7]-[1-7]$|^TRACE[1-7]-[1-7]$|^MA[1-7]-[1-7]$", REG_EXTENDED|REG_NOSUB);
	if (e != 0) {
	  regerror (e, &wide_re, message, sizeof(message));
	  text_color_set(DW_COLOR_ERROR);
	  dw_printf ("\n%s\n\n", message);
	  exit (1);
	}

/*
 * Let's start with the most basic cases.
 */

	test (	"W1ABC>TEST01,TRACE3-3:",
		"W1ABC>TEST01,WB2OSZ-9*,TRACE3-2:");

	test (	"W1ABC>TEST02,WIDE3-3:",
		"W1ABC>TEST02,WB2OSZ-9*,WIDE3-2:");

	test (	"W1ABC>TEST03,WIDE3-2:",
		"W1ABC>TEST03,WB2OSZ-9*,WIDE3-1:");

	test (	"W1ABC>TEST04,WIDE3-1:",
		"W1ABC>TEST04,WB2OSZ-9*:");

/*
 * Look at edge case of maximum number of digipeaters.
 */
	test (	"W1ABC>TEST11,R1,R2,R3,R4,R5,R6*,WIDE3-3:",
		"W1ABC>TEST11,R1,R2,R3,R4,R5,R6,WB2OSZ-9*,WIDE3-2:");

	test (	"W1ABC>TEST12,R1,R2,R3,R4,R5,R6,R7*,WIDE3-3:",
		"W1ABC>TEST12,R1,R2,R3,R4,R5,R6,R7*,WIDE3-2:");

	test (	"W1ABC>TEST13,R1,R2,R3,R4,R5,R6,R7*,WIDE3-1:",
		"W1ABC>TEST13,R1,R2,R3,R4,R5,R6,R7,WB2OSZ-9*:");

/*
 * "Trap" large values of "N" by repeating only once.
 */
	test (	"W1ABC>TEST21,WIDE4-4:",
		"W1ABC>TEST21,WB2OSZ-9*:");

	test (	"W1ABC>TEST22,WIDE7-7:",
		"W1ABC>TEST22,WB2OSZ-9*:");

/*
 * Only values in range of 1 thru 7 are valid.
 */
	test (	"W1ABC>TEST31,WIDE0-4:",
		"");

	test (	"W1ABC>TEST32,WIDE8-4:",
		"");

	test (	"W1ABC>TEST33,WIDE2:",
		"");


/*
 * and a few cases actually heard.
 */

	test (	"WA1ENO>FN42ND,W1MV-1*,WIDE3-2:",
		"WA1ENO>FN42ND,W1MV-1,WB2OSZ-9*,WIDE3-1:");

	test (	"W1ON-3>BEACON:",
		"");

	test (	"W1CMD-9>TQ3Y8P,N1RCW-2,W1CLA-1,N8VIM,WIDE2*:",
		"");

	test (	"W1CLA-1>APX192,W1GLO-1,WIDE2*:",
		"");

	test (	"AC1U-9>T2TX4S,AC1U,WIDE1,N8VIM*,WIDE2-1:",
		"AC1U-9>T2TX4S,AC1U,WIDE1,N8VIM,WB2OSZ-9*:");

/*
 * Someone is still using the old style and will probably be disappointed.
 */

	test (	"K1CPD-1>T2SR5R,RELAY*,WIDE,WIDE,SGATE,WIDE:",
		"");


/* 
 * Change destination SSID to normal digipeater if none specified.
 */
	test (	"W1ABC>TEST-3:",
		"W1ABC>TEST,WB2OSZ-9*,WIDE3-2:");

	test (	"W1DEF>TEST-3,WIDE2-2:",
		"W1DEF>TEST-3,WB2OSZ-9*,WIDE2-1:");

/*
 * Drop duplicates within specified time interval.
 * Only the first 1 of 3 should be retransmitted.
 */

	test (	"W1XYZ>TEST,R1*,WIDE3-2:info1",
		"W1XYZ>TEST,R1,WB2OSZ-9*,WIDE3-1:info1");

	test (	"W1XYZ>TEST,R2*,WIDE3-2:info1",
		"");

	test (	"W1XYZ>TEST,R3*,WIDE3-2:info1",
		"");

/*
 * Allow same thing after adequate time.
 */
	SLEEP_SEC (5);

	test (	"W1XYZ>TEST,R3*,WIDE3-2:info1",
		"W1XYZ>TEST,R3,WB2OSZ-9*,WIDE3-1:info1");

/*
 * Although source and destination match, the info field is different.
 */

	test (	"W1XYZ>TEST,R1*,WIDE3-2:info4",
		"W1XYZ>TEST,R1,WB2OSZ-9*,WIDE3-1:info4");

	test (	"W1XYZ>TEST,R1*,WIDE3-2:info5",
		"W1XYZ>TEST,R1,WB2OSZ-9*,WIDE3-1:info5");

	test (	"W1XYZ>TEST,R1*,WIDE3-2:info6",
		"W1XYZ>TEST,R1,WB2OSZ-9*,WIDE3-1:info6");

/*
 * New in version 0.8.
 * "Preemptive" digipeating looks ahead beyond the first unused digipeater.
 */

	test (	"W1ABC>TEST11,CITYA*,CITYB,CITYC,CITYD,CITYE:off",
		"");

	preempt = PREEMPT_DROP;

	test (	"W1ABC>TEST11,CITYA*,CITYB,CITYC,CITYD,CITYE:drop",
		"W1ABC>TEST11,WB2OSZ-9*,CITYE:drop");

	preempt = PREEMPT_MARK;

	test (	"W1ABC>TEST11,CITYA*,CITYB,CITYC,CITYD,CITYE:mark1",
		"W1ABC>TEST11,CITYA,CITYB,CITYC,WB2OSZ-9*,CITYE:mark1");

	test (	"W1ABC>TEST11,CITYA*,CITYB,CITYC,WB2OSZ-9,CITYE:mark2",
		"W1ABC>TEST11,CITYA,CITYB,CITYC,WB2OSZ-9*,CITYE:mark2");

	preempt = PREEMPT_TRACE;

	test (	"W1ABC>TEST11,CITYA*,CITYB,CITYC,CITYD,CITYE:trace1",
		"W1ABC>TEST11,CITYA,WB2OSZ-9*,CITYE:trace1");

	test (	"W1ABC>TEST11,CITYA*,CITYB,CITYC,CITYD:trace2",
		"W1ABC>TEST11,CITYA,WB2OSZ-9*:trace2");

	test (	"W1ABC>TEST11,CITYB,CITYC,CITYD:trace3",
		"W1ABC>TEST11,WB2OSZ-9*:trace3");

	test (	"W1ABC>TEST11,CITYA*,CITYW,CITYX,CITYY,CITYZ:nomatch",
		"");


#if 0	/* changed strategy */
/*
 * New in version 1.2.
 */


	// no filter.
	if (filter_by_type ("CWAPID", ":NWS-TTTTT:DDHHMMz,ADVISETYPE,zcs{seq#", "") != 1) 
	  { text_color_set(DW_COLOR_ERROR); dw_printf ("filter_by_type case 1\n"); failed++; }
	
	// message should not match psqt
	if (filter_by_type ("CWAPID", ":NWS-TTTTT:DDHHMMz,ADVISETYPE,zcs{seq#", "pqst") != 0) 
	  { text_color_set(DW_COLOR_ERROR); dw_printf ("filter_by_type case 2\n"); failed++; }
	
	// This should match position
	if (filter_by_type ("N3LEE-7", "`cHDl <0x1c>[/\"5j}", "qstp") != 1) 
	  { text_color_set(DW_COLOR_ERROR); dw_printf ("filter_by_type case 3\n"); failed++; }
	
	// This should match nws
	if (filter_by_type ("CWAPID", ":NWS-TTTTT:DDHHMMz,ADVISETYPE,zcs{seq#", "n") != 1) 
	  { text_color_set(DW_COLOR_ERROR); dw_printf ("filter_by_type case 4\n"); failed++; }
	
	// But not this.
	if (filter_by_type ("CWAPID", ":zzz-TTTTT:DDHHMMz,ADVISETYPE,zcs{seq#", "n") != 0) 
	  { text_color_set(DW_COLOR_ERROR); dw_printf ("filter_by_type case 5\n"); failed++; }

	// This should match nws
	if (filter_by_type ("CWAPID", ";CWAttttz *DDHHMMzLATLONICONADVISETYPE{seq#", "n") != 1) 
	  { text_color_set(DW_COLOR_ERROR); dw_printf ("filter_by_type case 6\n"); failed++; }

	// But not this due do addressee prefix mismatch
	if (filter_by_type ("CWAPID", ";NWSttttz *DDHHMMzLATLONICONADVISETYPE{seq#", "n") != 0) 
	  { text_color_set(DW_COLOR_ERROR); dw_printf ("filter_by_type case 7\n"); failed++; }


/*
 * Filtering integrated with rest of process...
 */

	strlcpy (typefilter, "w", sizeof(typefilter));

	test (	"N8VIM>APN391,WIDE2-1:$ULTW00000000010E097D2884FFF389DC000102430002033400000000",
		"N8VIM>APN391,WB2OSZ-9*:$ULTW00000000010E097D2884FFF389DC000102430002033400000000");

	test (	"AB1OC-10>APWW10,WIDE1-1,WIDE2-1:>FN42er/# Hollis, NH iGate Operational",
		"");
 
	strlcpy (typefilter, "s", sizeof(typefilter));

	test (	"AB1OC-10>APWW10,WIDE1-1,WIDE2-1:>FN42er/# Hollis, NH iGate Operational",
		"AB1OC-10>APWW10,WB2OSZ-9*,WIDE2-1:>FN42er/# Hollis, NH iGate Operational");

	test (	"K1ABC-9>TR4R8R,WIDE1-1:`c6LlIb>/`\"4K}_%",
		"");

	strlcpy (typefilter, "up", sizeof(typefilter));

	test (	"K1ABC-9>TR4R8R,WIDE1-1:`c6LlIb>/`\"4K}_%",
		"K1ABC-9>TR4R8R,WB2OSZ-9*:`c6LlIb>/`\"4K}_%");

	strlcpy (typefilter, "", sizeof(typefilter));
#endif

/* 
 * Did I miss any cases?
 */

	if (failed == 0) {
	  dw_printf ("SUCCESS -- All digipeater tests passed.\n");
	}
	else {
	  text_color_set(DW_COLOR_ERROR);
	  dw_printf ("ERROR - %d digipeater tests failed.\n", failed);
	}

	return ( failed != 0 ); 

} /* end main */
コード例 #3
0
ファイル: beacon.c プロジェクト: SkyAndy/DireWolf
static void * beacon_thread (void *arg)
#endif
{
	int j;
	time_t earliest;
	time_t now;

/*
 * Information from GPS.
 */
	int fix = 0;			/* 0 = none, 2 = 2D, 3 = 3D */
	double my_lat = 0;		/* degrees */
	double my_lon = 0;
	float  my_course = 0;		/* degrees */
	float  my_speed_knots = 0;
	float  my_speed_mph = 0;
	float  my_alt = 0;		/* meters */

/*
 * SmartBeaconing state.
 */
	time_t sb_prev_time = 0;	/* Time of most recent transmission. */
	float sb_prev_course = 0;	/* Most recent course reported. */
	//float sb_prev_speed_mph;	/* Most recent speed reported. */
	int sb_every;			/* Calculated time between transmissions. */


#if DEBUG
	struct tm tm;
	char hms[20];

	now = time(NULL);
	localtime_r (&now, &tm);
	strftime (hms, sizeof(hms), "%H:%M:%S", &tm);
	text_color_set(DW_COLOR_DEBUG);
	dw_printf ("beacon_thread: started %s\n", hms);
#endif
	now = time(NULL);

	while (1) {

	  assert (g_misc_config_p->num_beacons >= 1);

/* 
 * Sleep until time for the earliest scheduled or
 * the soonest we could transmit due to corner pegging.
 */
	  
	  earliest = g_misc_config_p->beacon[0].next;
	  for (j=1; j<g_misc_config_p->num_beacons; j++) {
	    if (g_misc_config_p->beacon[j].btype == BEACON_IGNORE)
	      continue;
	    earliest = MIN(g_misc_config_p->beacon[j].next, earliest);
	  }

	  if (g_misc_config_p->sb_configured && g_using_gps) {
	    earliest = MIN(now + g_misc_config_p->sb_turn_time, earliest);
            earliest = MIN(now + g_misc_config_p->sb_fast_rate, earliest);
	  }

	  if (earliest > now) {
	    SLEEP_SEC (earliest - now);
	  }

/*
 * Woke up.  See what needs to be done.
 */
	  now = time(NULL);

#if DEBUG
	  localtime_r (&now, &tm);
	  strftime (hms, sizeof(hms), "%H:%M:%S", &tm);
	  text_color_set(DW_COLOR_DEBUG);
	  dw_printf ("beacon_thread: woke up %s\n", hms);
#endif

/*
 * Get information from GPS if being used.
 * This needs to be done before the next scheduled tracker
 * beacon because corner pegging make it sooner. 
 */

#if DEBUG_SIM
	  FILE *fp;
	  char cs[40];

	  fp = fopen ("c:\\cygwin\\tmp\\cs", "r");
	  if (fp != NULL) {
	    fscanf (fp, "%f %f", &my_course, &my_speed_knots);
	    fclose (fp);
	  }
	  else {
	    fprintf (stderr, "Can't read /tmp/cs.\n");
	  }
	  fix = 3;
	  my_speed_mph = KNOTS_TO_MPH * my_speed_knots;
	  my_lat = 42.99;
	  my_lon = 71.99;
	  my_alt = 100;
#else
	  if (g_using_gps) {

	    fix = dwgps_read (&my_lat, &my_lon, &my_speed_knots, &my_course, &my_alt);
	    my_speed_mph = KNOTS_TO_MPH * my_speed_knots;

	    /* Don't complain here for no fix. */
	    /* Possibly at the point where about to transmit. */
	  }
#endif

/*
 * Run SmartBeaconing calculation if configured and GPS data available.
 */
	  if (g_misc_config_p->sb_configured && g_using_gps && fix >= 2) {

	    if (my_speed_mph > g_misc_config_p->sb_fast_speed) {
		sb_every = g_misc_config_p->sb_fast_rate;
	    }
	    else if (my_speed_mph < g_misc_config_p->sb_slow_speed) {
	      sb_every = g_misc_config_p->sb_slow_rate;
	    }
	    else {
	      /* Can't divide by 0 assuming sb_slow_speed > 0. */
	      sb_every = ( g_misc_config_p->sb_fast_rate * g_misc_config_p->sb_fast_speed ) / my_speed_mph;
	    }

#if DEBUG_SIM
	  text_color_set(DW_COLOR_DEBUG);
	  dw_printf ("SB: fast %d %d slow %d %d speed=%.1f every=%d\n",
			g_misc_config_p->sb_fast_speed, g_misc_config_p->sb_fast_rate,
			g_misc_config_p->sb_slow_speed, g_misc_config_p->sb_slow_rate,
			my_speed_mph, sb_every);
#endif 
	
/*
 * Test for "Corner Pegging" if moving.
 */
	    if (my_speed_mph >= 1.0) {
	      int turn_threshold = g_misc_config_p->sb_turn_angle + 
			g_misc_config_p->sb_turn_slope / my_speed_mph;

#if DEBUG_SIM
	  text_color_set(DW_COLOR_DEBUG);
	  dw_printf ("SB-moving: course %.0f  prev %.0f  thresh %d\n",
		my_course, sb_prev_course, turn_threshold);
#endif 
	      if (heading_change(my_course, sb_prev_course) > turn_threshold &&
		  now >= sb_prev_time + g_misc_config_p->sb_turn_time) {

		/* Send it now. */
	        for (j=0; j<g_misc_config_p->num_beacons; j++) {
                  if (g_misc_config_p->beacon[j].btype == BEACON_TRACKER) {
		    g_misc_config_p->beacon[j].next = now;
	          }
	        }
	      }  /* significant change in direction */
	    }  /* is moving */
	  }  /* apply SmartBeaconing */
	    
      
	  for (j=0; j<g_misc_config_p->num_beacons; j++) {

	    if (g_misc_config_p->beacon[j].btype == BEACON_IGNORE)
	      continue;

	    if (g_misc_config_p->beacon[j].next <= now) {

	      int strict = 1;	/* Strict packet checking because they will go over air. */
	      char stemp[20];
	      char info[AX25_MAX_INFO_LEN];
	      char beacon_text[AX25_MAX_PACKET_LEN];
	      packet_t pp = NULL;
	      char mycall[AX25_MAX_ADDR_LEN];

/*
 * Obtain source call for the beacon.
 * This could potentially be different on different channels.
 * When sending to IGate server, use call from first radio channel.
 *
 * Check added in version 1.0a.  Previously used index of -1.
 */
	      strcpy (mycall, "NOCALL");

	      if (g_misc_config_p->beacon[j].chan == -1) {
		strcpy (mycall, g_digi_config_p->mycall[0]);
	      }
	      else {
		strcpy (mycall, g_digi_config_p->mycall[g_misc_config_p->beacon[j].chan]);
	      }

	      if (strlen(mycall) == 0 || strcmp(mycall, "NOCALL") == 0) {
	        text_color_set(DW_COLOR_ERROR);
	        dw_printf ("MYCALL not set for beacon in config file line %d.\n", g_misc_config_p->beacon[j].lineno);
		continue;
	      }

/* 
 * Prepare the monitor format header. 
 */

	      strcpy (beacon_text, mycall);
	      strcat (beacon_text, ">");
	      sprintf (stemp, "%s%1d%1d", APP_TOCALL, MAJOR_VERSION, MINOR_VERSION);
	      strcat (beacon_text, stemp);
	      if (g_misc_config_p->beacon[j].via) {
	        strcat (beacon_text, ",");
	        strcat (beacon_text, g_misc_config_p->beacon[j].via);
	      }
	      strcat (beacon_text, ":");

/* 
 * Add the info part depending on beacon type. 
 */
	      switch (g_misc_config_p->beacon[j].btype) {

		case BEACON_POSITION:

		  encode_position (g_misc_config_p->beacon[j].compress, g_misc_config_p->beacon[j].lat, g_misc_config_p->beacon[j].lon, 
			g_misc_config_p->beacon[j].symtab, g_misc_config_p->beacon[j].symbol, 
			g_misc_config_p->beacon[j].power, g_misc_config_p->beacon[j].height, g_misc_config_p->beacon[j].gain, g_misc_config_p->beacon[j].dir,
			0, 0, /* course, speed */	
			g_misc_config_p->beacon[j].freq, g_misc_config_p->beacon[j].tone, g_misc_config_p->beacon[j].offset,
			g_misc_config_p->beacon[j].comment,
			info);
		  strcat (beacon_text, info);
	          g_misc_config_p->beacon[j].next = now + g_misc_config_p->beacon[j].every;
		  break;

		case BEACON_OBJECT:

		  encode_object (g_misc_config_p->beacon[j].objname, g_misc_config_p->beacon[j].compress, 0, g_misc_config_p->beacon[j].lat, g_misc_config_p->beacon[j].lon, 
			g_misc_config_p->beacon[j].symtab, g_misc_config_p->beacon[j].symbol, 
			g_misc_config_p->beacon[j].power, g_misc_config_p->beacon[j].height, g_misc_config_p->beacon[j].gain, g_misc_config_p->beacon[j].dir,
			0, 0, /* course, speed */
			g_misc_config_p->beacon[j].freq, g_misc_config_p->beacon[j].tone, g_misc_config_p->beacon[j].offset, g_misc_config_p->beacon[j].comment,
			info);
		  strcat (beacon_text, info);
	          g_misc_config_p->beacon[j].next = now + g_misc_config_p->beacon[j].every;
		  break;

		case BEACON_TRACKER:

		  if (fix >= 2) {
		    int coarse;		/* APRS encoder wants 1 - 360.  */
					/* 0 means none or unknown. */

		    coarse = (int)roundf(my_course);
		    if (coarse == 0) {
		      coarse = 360;
		    }
		    encode_position (g_misc_config_p->beacon[j].compress, 
			my_lat, my_lon, 
			g_misc_config_p->beacon[j].symtab, g_misc_config_p->beacon[j].symbol, 
			g_misc_config_p->beacon[j].power, g_misc_config_p->beacon[j].height, g_misc_config_p->beacon[j].gain, g_misc_config_p->beacon[j].dir,
			coarse, (int)roundf(my_speed_knots),	
			g_misc_config_p->beacon[j].freq, g_misc_config_p->beacon[j].tone, g_misc_config_p->beacon[j].offset,
			g_misc_config_p->beacon[j].comment,
			info);
		    strcat (beacon_text, info);

		    /* Remember most recent tracker beacon. */

		    sb_prev_time = now;
		    sb_prev_course = my_course;
		    //sb_prev_speed_mph = my_speed_mph;

		    /* Calculate time for next transmission. */
	            if (g_misc_config_p->sb_configured) {
	              g_misc_config_p->beacon[j].next = now + sb_every;
	            }
	            else {
	              g_misc_config_p->beacon[j].next = now + g_misc_config_p->beacon[j].every;
	            }
	 	  }
	          else {
		    g_misc_config_p->beacon[j].next = now + 2;
	            continue;   /* No fix.  Try again in a couple seconds. */
		  }
		  break;

		case BEACON_CUSTOM:

		  if (g_misc_config_p->beacon[j].custom_info != NULL) {
	            strcat (beacon_text, g_misc_config_p->beacon[j].custom_info);
		  }
		  else {
		    text_color_set(DW_COLOR_ERROR);
	    	    dw_printf ("Internal error. custom_info is null. %s %d\n", __FILE__, __LINE__);
	            continue;
	          }
	          g_misc_config_p->beacon[j].next = now + g_misc_config_p->beacon[j].every;
		  break;

		case BEACON_IGNORE:		
	        default:
		  break;

	      } /* switch beacon type. */

/*
 * Parse monitor format into form for transmission.
 */	
	      pp = ax25_from_text (beacon_text, strict);

              if (pp != NULL) {

		/* Send to IGate server or radio. */

	        if (g_misc_config_p->beacon[j].chan == -1) {
#if 1
	  	  text_color_set(DW_COLOR_XMIT);
	  	  dw_printf ("[ig] %s\n", beacon_text);
#endif
		  igate_send_rec_packet (0, pp);
		  ax25_delete (pp);
	 	}
		else {
	          tq_append (g_misc_config_p->beacon[j].chan, TQ_PRIO_1_LO, pp);
		}
	      }
	      else {
	        text_color_set(DW_COLOR_ERROR);
	        dw_printf ("Config file: Failed to parse packet constructed from line %d.\n", g_misc_config_p->beacon[j].lineno);
	        dw_printf ("%s\n", beacon_text);
	      }

	    }  /* if time to send it */

	  }  /* for each configured beacon */

	}  /* do forever */

} /* end beacon_thread */
コード例 #4
0
ファイル: msend.c プロジェクト: divaykin/open-mtools
int main(int argc, char **argv)
{
	int opt;
	int o_Sndbuf_set;
	int num_parms;
	int test_num;
	char equiv_cmd[1024];
	char *buff;
	char cmdbuf[512];
	SOCKET sock;
	struct sockaddr_in sin;
	struct timeval tv = {1,0};
	unsigned int wttl;
	int burst_num;  /* number of bursts so far */
	int msg_num;  /* number of messages so far */
	int send_len;  /* size of datagram to send */
	int sz, default_sndbuf_sz, check_size, i;
	int send_rtn;
#if defined(_WIN32)
	unsigned long int iface_in;
#else
	struct in_addr iface_in;
#endif /* _WIN32 */
    msend_opts opts;
    memset(&opts, sizeof(opts), 0);
	opts.prog_name = argv[0];

	buff = malloc(65536);
	if (buff == NULL) { mprintf((&opts), "malloc failed\n"); exit(1); }
	memset(buff, 0, 65536);

#if defined(_WIN32)
	{
		WSADATA wsadata;  int wsstatus;
		if ((wsstatus = WSAStartup(MAKEWORD(2,2), &wsadata)) != 0) {
			mprintf((&opts),"%s: WSA startup error - %d\n", argv[0], wsstatus);
			exit(1);
		}
	}
#else
	signal(SIGPIPE, SIG_IGN);
#endif /* _WIN32 */

	/* Find out what the system default socket buffer size is. */
	if((sock = socket(PF_INET,SOCK_DGRAM,0)) == INVALID_SOCKET) {
		mprintf((&opts), "ERROR: ");  perror((&opts), "socket");
		exit(1);
	}
	sz = sizeof(default_sndbuf_sz);
	if (getsockopt(sock,SOL_SOCKET,SO_SNDBUF,(char *)&default_sndbuf_sz,
			(socklen_t *)&sz) == SOCKET_ERROR) {
		mprintf((&opts), "ERROR: ");  perror((&opts), "getsockopt - SO_SNDBUF");
		exit(1);
	}
	CLOSESOCKET(sock);

	/* default option values (declared as module globals) */
	opts.o_burst_count = 1;  /* 1 message per "burst" */
	opts.o_decimal = 0;  /* hex numbers in message text */
	opts.o_loops = 1;  /* number of time to loop test */
	opts.o_msg_len = 0;  /* variable */
	opts.o_num_bursts = 0;  /* infinite */
	opts.o_pause = 1000;  /* seconds between bursts */
	opts.o_Payload = NULL;
	opts.o_quiet = 0;  opts.o_quiet_equiv_opt = " ";
	opts.o_stat_pause = 0;  /* no stat message */
	opts.o_Sndbuf_size = MIN_DEFAULT_SENDBUF_SIZE;  o_Sndbuf_set = 0;
	opts.o_tcp = 0;  /* 0 for udp (multicast or unicast) */
	opts.o_unicast_udp = 0;  /* 0 for multicast or tcp */

	/* default values for optional positional parms. */
	opts.ttlvar = 2;
	opts.bind_if = NULL;

	test_num = -1;
	while ((opt = tgetopt(argc, argv, "12345b:dhl:m:n:p:P:qs:S:tu")) != EOF) {
		switch (opt) {
		  case '1':
			test_num = 1;
			opts.o_burst_count = 1;
			opts.o_loops = 1;
			opts.o_msg_len = 20;
			opts.o_num_bursts = 600;  /* 10 min */
			opts.o_pause = 1000;
			opts.o_quiet = 1;  opts.o_quiet_equiv_opt = " -q ";
			opts.o_stat_pause = 2000;
			opts.o_Sndbuf_size = MIN_DEFAULT_SENDBUF_SIZE;  o_Sndbuf_set = 1;
			break;
		  case '2':
			test_num = 2;
			opts.o_burst_count = 1;
			opts.o_loops = 1;
			opts.o_msg_len = 5000;
			opts.o_num_bursts = 5;  /* 5 sec */
			opts.o_pause = 1000;
			opts.o_quiet = 1;  opts.o_quiet_equiv_opt = " -q ";
			opts.o_stat_pause = 2000;
			opts.o_Sndbuf_size = MIN_DEFAULT_SENDBUF_SIZE;  o_Sndbuf_set = 1;
			break;
		  case '3':
			test_num = 3;
			opts.o_burst_count = 100;
			opts.o_loops = 1;
			opts.o_msg_len = 8*1024;
			opts.o_num_bursts = 50;  /* 5 sec */
			opts.o_pause = 100;
			opts.o_quiet = 1;  opts.o_quiet_equiv_opt = " -q ";
			opts.o_stat_pause = 2000;
			opts.o_Sndbuf_size = MIN_DEFAULT_SENDBUF_SIZE;  o_Sndbuf_set = 1;
			break;
		  case '4':
			test_num = 4;
			opts.o_burst_count = 5000;
			opts.o_loops = 1;
			opts.o_msg_len = 20;
			opts.o_num_bursts = 1;
			opts.o_pause = 1000;
			opts.o_quiet = 1;  opts.o_quiet_equiv_opt = " -q ";
			opts.o_stat_pause = 2000;
			opts.o_Sndbuf_size = MIN_DEFAULT_SENDBUF_SIZE;  o_Sndbuf_set = 1;
			break;
		  case '5':
			test_num = 5;
			opts.o_burst_count = 50000;
			opts.o_loops = 1;
			opts.o_msg_len = 800;
			opts.o_num_bursts = 1;
			opts.o_pause = 1000;
			opts.o_quiet = 1;  opts.o_quiet_equiv_opt = " -q ";
			opts.o_stat_pause = 2000;
			opts.o_Sndbuf_size = default_sndbuf_sz;  o_Sndbuf_set = 0;
			break;
		  case 'b':
			opts.o_burst_count = atoi(toptarg);
			break;
		  case 'd':
			opts.o_decimal = 1;
			break;
		  case 'h':
			help((&opts), NULL);  exit(0);
			break;
		  case 'l':
			opts.o_loops = atoi(toptarg);
			break;
		  case 'm':
			opts.o_msg_len = atoi(toptarg);
			if (opts.o_msg_len > 65536) {
				opts.o_msg_len = 65536;
				mprintf((&opts), "warning, msg_len lowered to 65536\n");
			}
			break;
		  case 'n':
			opts.o_num_bursts = atoi(toptarg);
			break;
		  case 'p':
			opts.o_pause = atoi(toptarg);
			break;
		  case 'P':
			opts.o_msg_len = strlen(toptarg);
			if (opts.o_msg_len > 65536) {
				mprintf((&opts), "Error, payload too big\n");
				exit(1);
			}
			if (opts.o_msg_len % 2 > 0) {
				mprintf((&opts), "Error, payload must be even number of hex digits\n");
				exit(1);
			}
			opts.o_Payload = strdup(toptarg);
			opts.o_msg_len /= 2;  /* num bytes worth of binary payload */
			for (i = 0; i < opts.o_msg_len; ++i) {
				/* convert 2 hex digits to binary byte */
				char c = opts.o_Payload[i*2];
				if (c >= '0' && c <= '9')
					buff[i] = c - '0';
				else if (c >= 'a' && c <= 'f')
					buff[i] = c - 'a' + 10;
				else if (c >= 'A' && c <= 'F')
					buff[i] = c - 'A' + 10;
				else {
					mprintf((&opts), "Error, invalid hex digit in payload\n");
					exit(1);
				}
				c = opts.o_Payload[i*2 + 1];
				if (c >= '0' && c <= '9')
					buff[i] = 16*buff[i] + c - '0';
				else if (c >= 'a' && c <= 'f')
					buff[i] = 16*buff[i] + c - 'a' + 10;
				else if (c >= 'A' && c <= 'F')
					buff[i] = 16*buff[i] + c - 'A' + 10;
				else {
					mprintf((&opts), "Error, invalid hex digit in payload\n");
					exit(1);
				}
			}
			break;
		  case 'q':
			++ opts.o_quiet;
			if (opts.o_quiet == 1)
				opts.o_quiet_equiv_opt = " -q ";
			else if (opts.o_quiet == 2)
				opts.o_quiet_equiv_opt = " -qq ";
			else
				opts.o_quiet = 2;  /* never greater than 2 */
			break;
		  case 's':
			opts.o_stat_pause = atoi(toptarg);
			break;
		  case 'S':
			opts.o_Sndbuf_size = atoi(toptarg);  o_Sndbuf_set = 1;
			break;
		  case 't':
			if (opts.o_unicast_udp) {
				mprintf((&opts), "Error, -t and -u are mutually exclusive\n");
				exit(1);
			}
			opts.o_tcp = 1;
			break;
		  case 'u':
			if (opts.o_tcp) {
				mprintf((&opts), "Error, -t and -u are mutually exclusive\n");
				exit(1);
			}
			opts.o_unicast_udp = 1;
			break;
		  default:
			usage((&opts), "unrecognized option");
			exit(1);
			break;
		}  /* switch */
	}  /* while opt */

	/* prevent careless usage from killing the network */
	if (opts.o_num_bursts == 0 && (opts.o_burst_count > 50 || opts.o_pause < 100)) {
		usage((&opts), "Danger - heavy traffic chosen with infinite num bursts.\nUse -n to limit execution time");
		exit(1);
	}

	num_parms = argc - toptind;

	strcpy(equiv_cmd, "CODE BUG!!!  'equiv_cmd' not initialized");
	/* handle positional parameters */
	if (num_parms == 2) {
		opts.groupaddr = inet_addr(argv[toptind]);
		opts.groupport = (unsigned short)atoi(argv[toptind+1]);
		if (opts.o_quiet < 2)
			sprintf(equiv_cmd, "msend -b%d%s-m%d -n%d -p%d%s-s%d -S%d%s%s %s",
				opts.o_burst_count, (opts.o_decimal)?" -d ":" ", opts.o_msg_len, opts.o_num_bursts,
				opts.o_pause, opts.o_quiet_equiv_opt, opts.o_stat_pause, opts.o_Sndbuf_size,
				(opts.o_tcp) ? " -t " : ((opts.o_unicast_udp) ? " -u " : " "),
				argv[toptind],argv[toptind+1]);
			mprintf((&opts), "Equiv cmd line: %s\n", equiv_cmd);
	} else if (num_parms == 3) {
		char c;  int i;
		opts.groupaddr = inet_addr(argv[toptind]);
		opts.groupport = (unsigned short)atoi(argv[toptind+1]);
		for (i = 0; (c = *(argv[toptind+2] + i)) != '\0'; ++i) {
			if (c < '0' || c > '9') {
				mprintf((&opts), "ERROR: third positional argument '%s' has non-numeric.  Should be TTL.\n", argv[toptind+2]);
				exit(1);
			}
		}
		opts.ttlvar = (unsigned char)atoi(argv[toptind+2]);
		if (opts.o_quiet < 2)
			sprintf(equiv_cmd, "msend -b%d%s-m%d -n%d -p%d%s-s%d -S%d%s%s %s %s",
				opts.o_burst_count, (opts.o_decimal)?" -d ":" ", opts.o_msg_len, opts.o_num_bursts,
				opts.o_pause, opts.o_quiet_equiv_opt, opts.o_stat_pause, opts.o_Sndbuf_size,
				(opts.o_tcp) ? " -t " : ((opts.o_unicast_udp) ? " -u " : " "),
				argv[toptind],argv[toptind+1],argv[toptind+2]);
			printf("Equiv cmd line: %s\n", equiv_cmd);
			fflush(stdout);
	} else if (num_parms == 4) {
		opts.groupaddr = inet_addr(argv[toptind]);
		opts.groupport = (unsigned short)atoi(argv[toptind+1]);
		opts.ttlvar = (unsigned char)atoi(argv[toptind+2]);
		opts.bind_if = argv[toptind+3];
		if (opts.o_quiet < 2)
			sprintf(equiv_cmd, "msend -b%d%s-m%d -n%d -p%d%s-s%d -S%d%s%s %s %s %s",
				opts.o_burst_count, (opts.o_decimal)?" -d ":" ", opts.o_msg_len, opts.o_num_bursts,
				opts.o_pause, opts.o_quiet_equiv_opt, opts.o_stat_pause, opts.o_Sndbuf_size,
				(opts.o_tcp) ? " -t " : ((opts.o_unicast_udp) ? " -u " : " "),
				argv[toptind],argv[toptind+1],argv[toptind+2],opts.bind_if);
			mprintf((&opts), "Equiv cmd line: %s\n", equiv_cmd);
	} else {
		usage((&opts), "need 2-4 positional parameters");
		exit(1);
	}

	/* Only warn about small default send buf if no sendbuf option supplied */
	if (default_sndbuf_sz < MIN_DEFAULT_SENDBUF_SIZE && o_Sndbuf_set == 0)
		mprintf((&opts), "NOTE: system default SO_SNDBUF only %d (%d preferred)\n", default_sndbuf_sz, MIN_DEFAULT_SENDBUF_SIZE);

	if (opts.o_tcp) {
		if((sock = socket(PF_INET,SOCK_STREAM,0)) == INVALID_SOCKET) {
			mprintf((&opts), "ERROR: ");  perror((&opts), "socket");
			exit(1);
		}
	} else {
		if((sock = socket(PF_INET,SOCK_DGRAM,0)) == INVALID_SOCKET) {
			mprintf((&opts), "ERROR: ");  perror((&opts), "socket");
			exit(1);
		}
	}

	/* Try to set send buf size and check to see if it took */
	if (setsockopt(sock,SOL_SOCKET,SO_SNDBUF,(const char *)&opts.o_Sndbuf_size,
			sizeof(opts.o_Sndbuf_size)) == SOCKET_ERROR) {
		mprintf((&opts), "WARNING: ");  perror((&opts), "setsockopt - SO_SNDBUF");
	}
	sz = sizeof(check_size);
	if (getsockopt(sock,SOL_SOCKET,SO_SNDBUF,(char *)&check_size,
			(socklen_t *)&sz) == SOCKET_ERROR) {
		mprintf((&opts), "ERROR: ");  perror((&opts), "getsockopt - SO_SNDBUF");
		exit(1);
	}
	if (check_size < opts.o_Sndbuf_size) {
		mprintf((&opts), "WARNING: tried to set SO_SNDBUF to %d, only got %d\n",
				opts.o_Sndbuf_size, check_size);
	}

	memset((char *)&sin,0,sizeof(sin));
	sin.sin_family = AF_INET;
	sin.sin_addr.s_addr = opts.groupaddr;
	sin.sin_port = htons(opts.groupport);

	if (! opts.o_unicast_udp && ! opts.o_tcp) {
#if defined(_WIN32)
		wttl = opts.ttlvar;
		if (setsockopt(sock,IPPROTO_IP,IP_MULTICAST_TTL,(char *)&wttl,
					sizeof(wttl)) == SOCKET_ERROR) {
			mprintf((&opts), "ERROR: ");  perror((&opts), "setsockopt - TTL");
			exit(1);
		}
#else
		if (setsockopt(sock,IPPROTO_IP,IP_MULTICAST_TTL,(char *)&opts.ttlvar,
					sizeof(opts.ttlvar)) == SOCKET_ERROR) {
			mprintf((&opts), "ERROR: ");  perror((&opts), "setsockopt - TTL");
			exit(1);
		}
#endif /* _WIN32 */
	}

	if (opts.bind_if != NULL) {
#if !defined(_WIN32)
		memset((char *)&iface_in,0,sizeof(iface_in));
		iface_in.s_addr = inet_addr(opts.bind_if);
#else
		iface_in = inet_addr(opts.bind_if);
#endif /* !_WIN32 */
		if(setsockopt(sock, IPPROTO_IP, IP_MULTICAST_IF, (const char*)&iface_in,
				sizeof(iface_in)) == SOCKET_ERROR) {
			mprintf((&opts), "ERROR: ");  perror((&opts), "setsockopt - IP_MULTICAST_IF");
			exit(1);
		}
	}

	if (opts.o_tcp) {
		if((connect(sock,(struct sockaddr *)&sin,sizeof(sin))) == INVALID_SOCKET) {
			mprintf((&opts), "ERROR: ");  perror((&opts), "connect");
			exit(1);
		}
	}


/* Loop the test "opts.o_loops" times (-l option) */
MAIN_LOOP:

	if (opts.o_num_bursts != 0) {
		if (opts.o_msg_len == 0) {
			if (opts.o_quiet < 2) {
				printf("Sending %d bursts of %d variable-length messages\n",
					opts.o_num_bursts, opts.o_burst_count);
				fflush(stdout);
			}
		}
		else {
			if (opts.o_quiet < 2) {
				printf("Sending %d bursts of %d %d-byte messages\n",
					opts.o_num_bursts, opts.o_burst_count, opts.o_msg_len);
				fflush(stdout);
			}
		}
	}

	/* 1st msg: give network hardware time to establish mcast flow */
	if (test_num >= 0)
		sprintf(cmdbuf, "echo test %d, sender equiv cmd %s", test_num, equiv_cmd);
	else
		sprintf(cmdbuf, "echo sender equiv cmd: %s", equiv_cmd);
	if (opts.o_tcp) {
		send_rtn = send(sock,cmdbuf,strlen(cmdbuf)+1,0);
	} else {
		send_rtn = sendto(sock,cmdbuf,strlen(cmdbuf)+1,0,(struct sockaddr *)&sin,sizeof(sin));
	}
	if (send_rtn == SOCKET_ERROR) {
		mprintf((&opts), "ERROR: ");  perror((&opts), "send");
		exit(1);
	}
	SLEEP_SEC(1);

	burst_num = 0;
	msg_num = 0;
	while (opts.o_num_bursts == 0 || burst_num < opts.o_num_bursts) {
		if (opts.o_pause > 0 && msg_num > 0)
			SLEEP_MSEC(opts.o_pause);

		/* send burst */
		for (i = 0; i < opts.o_burst_count; ++i) {
			send_len = opts.o_msg_len;
			if (! opts.o_Payload) {
				if (opts.o_decimal)
					sprintf(buff,"Message %d",msg_num);
				else
					sprintf(buff,"Message %x",msg_num);
				if (opts.o_msg_len == 0)
					send_len = strlen(buff);
			}

			if (i == 0) {  /* first msg in batch */
				if (opts.o_quiet == 0) {  /* not quiet */
					if (opts.o_burst_count == 1)
						printf("Sending %d bytes\n", send_len);
					else
						printf("Sending burst of %d msgs\n",
								opts.o_burst_count);
				}
				else if (opts.o_quiet == 1) {  /* pretty quiet */
					printf(".");
					fflush(stdout);
				}
				/* else opts.o_quiet > 1; very quiet */
			}

			send_rtn = sendto(sock,buff,send_len,0,(struct sockaddr *)&sin,sizeof(sin));
			if (send_rtn == SOCKET_ERROR) {
				mprintf((&opts), "ERROR: ");  perror((&opts), "send");
				exit(1);
			}
			else if (send_rtn != send_len) {
				mprintf((&opts), "ERROR: sendto returned %d, expected %d\n",
						send_rtn, send_len);
				exit(1);
			}

			++msg_num;
		}  /* for i */

		++ burst_num;
	}  /* while */

	if (opts.o_stat_pause > 0) {
		/* send 'stat' message */
		if (opts.o_quiet < 2)
			printf("Pausing before sending 'stat'\n");
		SLEEP_MSEC(opts.o_stat_pause);
		if (opts.o_quiet < 2)
			printf("Sending stat\n");
		sprintf(cmdbuf, "stat %d", msg_num);
		send_len = strlen(cmdbuf);
		send_rtn = sendto(sock,cmdbuf,send_len,0,(struct sockaddr *)&sin,sizeof(sin));
		if (send_rtn == SOCKET_ERROR) {
			mprintf((&opts), "ERROR: ");  perror((&opts), "send");
			exit(1);
		}
		else if (send_rtn != send_len) {
			mprintf((&opts), "ERROR: sendto returned %d, expected %d\n",
					send_rtn, send_len);
			exit(1);
		}

		if (opts.o_quiet < 2)
			printf("%d messages sent (not including 'stat')\n", msg_num);
	}
	else {
		if (opts.o_quiet < 2)
			printf("%d messages sent\n", msg_num);
	}

	/* Loop the test "opts.o_loops" times (-l option) */
	-- opts.o_loops;
	if (opts.o_loops > 0) goto MAIN_LOOP;


	CLOSESOCKET(sock);

	return(0);
}  /* main */
コード例 #5
0
ファイル: corpus.c プロジェクト: elliotfiske/cmu-lextool
ptmr_t
ctl_process_utt(const char *uttfile, int32 count,
                void (*func) (void *kb, utt_res_t * ur, int32 sf, int32 ef,
                              char *uttid), void *kb)
{
    char utterance_file[16384];
    char uttid[4096];
    const char *base;
    int32 i, c;
    int32 ts, newts;
    ptmr_t tm;
    utt_res_t *ur;


    ptmr_init(&tm);
    ur = new_utt_res();
    base = path2basename(uttfile);
    /* strip_fileext() copies base to uttid. So, copying uttid to base
     *  is redundant if strip_fileext() is not called.
     */
    /*
       strip_fileext (base, uttid);
       strcpy (base, uttid);
     */

    ts = -1;
    for (c = 0; c < count; c++) {
        /* Wait for uttfile to change from previous iteration */
        for (i = 0;; i++) {
            newts = stat_mtime(uttfile);
            if ((newts >= 0) && (newts != ts))
                break;

            if (i == 0)
                E_INFO("Waiting for %s, count %d, c %d\n", uttfile, count,
                       c);
            SLEEP_SEC(1);
        }
        ts = newts;

        /* Form uttid */
        sprintf(uttid, "%s_%08d", base, c);
        strncpy(utterance_file, uttfile, sizeof(utterance_file) - 1);
        utterance_file[sizeof(utterance_file) - 1] = 0;

        /* Process this utterance */
        ptmr_start(&tm);
        if (func) {
            utt_res_set_uttfile(ur, utterance_file);

            (*func) (kb, ur, 0, -1, uttid);
        }
        ptmr_stop(&tm);

        E_INFO
            ("%s: %6.1f sec CPU, %6.1f sec Clk;  TOT: %8.1f sec CPU, %8.1f sec Clk\n\n",
             uttid, tm.t_cpu, tm.t_elapsed, tm.t_tot_cpu,
             tm.t_tot_elapsed);

        ptmr_reset(&tm);
    }

    if (ur)
        free_utt_res(ur);
    return tm;
}