Beispiel #1
0
/*----------------------------------------------------------------------
 *	see if a word will fit
 *	return number of letters successfully fitted
 *----------------------------------------------------------------------*/
int fit_word(char line[], Map allow[],	/* contents of board */
	     char *bused)		/* values of blanks used */
{
  int i;
  char c, *match, *word = play.word;
  static char tile[7+1];
  int nblank;

  /* first check that the letters are admissable */
  for (i=0; i<len; i++) {
    if (! in_map(allow[i], word[i])) {	/* impossible letter */
      return i;
    }
  }

  /* now check that the word can be made from the letters available */
  strcpy(tile, tile_rack.tile);
  nblank = tile_rack.nblank;
  for (i=0; i<len; i++) {
    if (line[i]==EMPTY) {		/* need to place a tile */
      c = word[i];
      if ((match = strchr(tile, c)) != NULL) {
	*match = EMPTY;			/* use up the tile */
      }else if (nblank != 0) {
	--nblank;			/* use a blank tile */
	*bused++ = c;			/* record what it replaced */
      }else{
	return i;
      }
    }
  }
  *bused = '\0';
  return len;
}
Beispiel #2
0
void print_map(Map map)
{
  int c;
  for (c='A'; c<='Z'; c++) {
    if (in_map(map,c)) printf("%c", c);
  }
}
Beispiel #3
0
/* Iterates though the string to find the next start of a suffix in a string.
 * Its like strtok/strsep, except hopefully less shitty. (no modifying the input)
 * start_map is a bit map of characters for which seeing indicates the start of a
 * new suffix.
 * middle_map is a bit map of characters for which seeing indicates that the next
 * characters to be seen not in middle_map is the start of a suffix
 * last_token is the index of the last found start, it should be <0 on first call
 * If there are no more suffixes left in the string, next_start returns -1
 * 0 Is always the start of a new suffix, unless it starts with a middle
 * character, in which case the first suffix is the first non middle character
 */
int next_start(string_data* string,
               parser_data* parser,
               int last_token) {
  if(string == NULL || parser == NULL)
    return -2;
  int token_start = last_token < 0 ? 0 : last_token + 1;
  /* If this is the first call we start in "middle mode", where any non-middle
   * character starts a suffix
   */
  int prev_middle = token_start == 0 ? 1 : 0;

  for(int c = token_start; c < string->length; c++) {
    int is_middle = in_map(parser->middle_map, string->normalized[c]);
    if((prev_middle && !is_middle) ||
        in_map(parser->start_map, string->normalized[c])) {
      return c;
    }
    prev_middle = is_middle;
  }
  /* Reached the end of the string, no more suffixes*/
  return -1;
}
Beispiel #4
0
/*----------------------------------------------------------------------
 *	Try inserting every available character into a gap and see
 *	which of them make words.
 *----------------------------------------------------------------------*/
static Map try_gap(char *word, int len,	/* word containing a hole */
		   int pos,		/* position of hole */
		   Map available)	/* which letters the player has */
{
  int c;
  Map map;
  
  map = empty_map;
  for (c='A'; c<='Z'; c++) {
    if (in_map(available, c)) {		/* only try those available */
      word[pos] = c;
      if (Dict_isword(dict, word, len)) {
	add_map(map, c);		/* record word possible */
      }
    }
  }
  return map;
}
static void overfill_lake(int x, int y, Shoreline * shore, int lake_id)
{
	// Starting point is a local minimum
	// Lake growth is done iteratively by flooding the lowest shore point and rising water level
	// shore point = neighbour without water 
	//      (at this point we have no water in the map, except other lakes and rivers)
	//
	// We have a list of shore points sorted by altitude

	int i, level;

	if (is_border(x, y))
		return;

	set_river_tile(x, y);
	level = ALT(x, y);

	// find neighbours
	for (i = 0; i < 8; i++) {
		if (in_map(x + di[i], y + dj[i]) && !IS_WATER(x + di[i], y + dj[i]))
			try_shore_point(x + di[i], y + dj[i], shore);
	}

	if (shore->next != NULL) {
		shore = shore->next;
		x = shore->x;
		y = shore->y;

		if ((ALT(x, y) < level)) {
			set_river_tile(x, y);
			// create river and continue to build shoreline
			// we will continue to overfill (from a lower point) until we reach border of the map
			//fprintf(stdout, "We found a pass x %i, y %i, alt %i \n", x, y, ALT(x,y));
			setup_one_river(x, y, lake_id, shore);
		}
		overfill_lake(x, y, shore, lake_id);
	} else {
		// Q: ? Should this happen ?
		// A: yes if we are in a lake that was previously filled by a higher one which overfilled here
		//    else ? it should not happen ?
		//fprintf(stderr,"the shoreline list is empty, x = %i, y = %i\n", x, y);
	}
}
static int setup_one_river(int xx, int yy, int lake_id, Shoreline * shore)
{
	int alt_max, x, y, alt, x0, y0;
	// start a river from point (xx, yy)
	set_river_tile(xx, yy);
	alt_max = ALT(xx, yy);

	x0 = xx;
	y0 = yy;
	/* follow most important slope and go downward */
	while (((xx != x) || (yy != y)) && (xx != 0) && (xx != (WORLD_SIDE_LEN - 1)) && (yy != 0)
	       && (yy != WORLD_SIDE_LEN - 1)) {
		int m = 0;
		x = xx;
		y = yy;
		alt = ALT(x, y);
		for (int n = 0; n < 8; n++) {
			if (in_map(x + di[n], y + dj[n])) {
				if (ALT(x + di[n], y + dj[n]) < alt) {
					xx = x + di[n];
					yy = y + dj[n];
					alt = ALT(xx, yy);
					m = n;
				}
				// find neighbours and update shore line if needed
				// may mark as shoreline a point which will be set as river later. We don't care
				if (!IS_WATER(x + di[n], y + dj[n]))
					try_shore_point(x + di[n], y + dj[n], shore);
			}
		}

		set_river_tile(xx, yy);
		if (m > 3) {
			// we did diagonal move, so we need to connect river
			if (ALT(x + di[m], y) > ALT(x, y + dj[m]))
				set_river_tile(x, y + dj[m]);
			else
				set_river_tile(x + di[m], y);
		}
	};
	// We are in a local minimum or at the borders of the map (strictly the lowest points)

}
std::tuple<boost::shared_ptr<Map_Matrix<DataFormat> >, std::string, GeoTransform>  read_in_map(fs::path file_path, GDALDataType data_type, const bool doCategorise) throw(std::runtime_error)
{

    std::string projection;
    GeoTransform transformation;
    GDALDriver driver;
    
	//Check that the file name is valid
	if (!(fs::is_regular_file(file_path)))
	{
		throw std::runtime_error("Input file is not a regular file");
	}	

	// Get GDAL to open the file - code is based on the tutorial at http://www.gdal.org/gdal_tutorial.html
	GDALDataset *poDataset;
	GDALAllRegister(); //This registers all availble raster file formats for use with this utility. How neat is that. We can input any GDAL supported rater file format.

	//Open the Raster by calling GDALOpen. http://www.gdal.org/gdal_8h.html#a6836f0f810396c5e45622c8ef94624d4
	//char pszfilename[] = file_path.c_str(); //Set this to the file name, as GDALOpen requires the standard C char pointer as function parameter.
	poDataset = (GDALDataset *) GDALOpen (file_path.string().c_str(), GA_ReadOnly);
	if (poDataset == NULL)
	{
		throw std::runtime_error("Unable to open file");
	}
	
//	Print some general information about the raster
	double        adfGeoTransform[6]; //An array of doubles that will be used to save information about the raster - where the origin is, what the raster pizel size is.
    
    
    printf( "Driver: %s/%s\n",
            poDataset->GetDriver()->GetDescription(),
            poDataset->GetDriver()->GetMetadataItem( GDAL_DMD_LONGNAME ) );

    printf( "Size is %dx%dx%d\n", 
            poDataset->GetRasterXSize(), poDataset->GetRasterYSize(),
            poDataset->GetRasterCount() );

    if( poDataset->GetProjectionRef()  != NULL )
    {
        printf( "Projection is `%s'\n", poDataset->GetProjectionRef() );
        projection = poDataset->GetProjectionRef();
    }

    if( poDataset->GetGeoTransform( adfGeoTransform ) == CE_None )
    {
        printf( "Origin = (%.6f,%.6f)\n",
                adfGeoTransform[0], adfGeoTransform[3] );

        printf( "Pixel Size = (%.6f,%.6f)\n",
                adfGeoTransform[1], adfGeoTransform[5] );
        
        transformation.x_origin = adfGeoTransform[0];
        transformation.pixel_width = adfGeoTransform[1];
        transformation.x_line_space = adfGeoTransform[2];
        transformation.y_origin = adfGeoTransform[3];
        transformation.pixel_height = adfGeoTransform[4];
        transformation.y_line_space = adfGeoTransform[5];
        
    }


	/// Some raster file formats allow many layers of data (called a 'band', with each having the same pixel size and origin location and spatial extent). We will get the data for the first layer into a Boost Array.
	//Get the data from the first band, 
	// TODO implement method with input to specify what band.
	    GDALRasterBand  *poBand;
        int             nBlockXSize, nBlockYSize;
        int             bGotMin, bGotMax;
        double          adfMinMax[2];
        
        poBand = poDataset->GetRasterBand( 1 );
        poBand->GetBlockSize( &nBlockXSize, &nBlockYSize );
        printf( "Block=%dx%d Type=%s, ColorInterp=%s\n",
                nBlockXSize, nBlockYSize,
                GDALGetDataTypeName(poBand->GetRasterDataType()),
                GDALGetColorInterpretationName(
                    poBand->GetColorInterpretation()) );

        adfMinMax[0] = poBand->GetMinimum( &bGotMin );
        adfMinMax[1] = poBand->GetMaximum( &bGotMax );
        if( ! (bGotMin && bGotMax) )
            GDALComputeRasterMinMax((GDALRasterBandH)poBand, TRUE, adfMinMax);

        printf( "Min=%.3fd, Max=%.3f\n", adfMinMax[0], adfMinMax[1] );
        
        if( poBand->GetOverviewCount() > 0 )
            printf( "Band has %d overviews.\n", poBand->GetOverviewCount() );

        if( poBand->GetColorTable() != NULL )
            printf( "Band has a color table with %d entries.\n", 
                     poBand->GetColorTable()->GetColorEntryCount() );

		DataFormat * pafScanline;
        int   nXSize = poBand->GetXSize();
		int   nYSize = poBand->GetYSize();
		boost::shared_ptr<Map_Matrix<DataFormat> > in_map(new Map_Matrix<DataFormat>(nYSize, nXSize));
		//get a c array of this size and read into this.
		
		
		//pafScanline = new DataFormat[nXSize];
		//for (int i = 0; i < nYSize; i++) //rows
		//{
		//	poBand->RasterIO(GF_Read, 0, i, nXSize, 1,
		//		pafScanline, nXSize, 1, data_type,
		//		0, 0);
		//	for (int j = 0; j < nXSize; j++) //cols
		//	{
		//		in_map->Get(i, j) = pafScanline[j];
		//	}
		//}
    
        //get a c array of this size and read into this.
        pafScanline = new DataFormat[nXSize * nYSize];
        //pafScanline = (float *) CPLMalloc(sizeof(float)*nXSize);
        poBand->RasterIO( GF_Read, 0, 0, nXSize, nYSize, 
			pafScanline, nXSize, nYSize, data_type,
                          0, 0 );
    
        //Copy into Map_Matrix.
        int pafIterator = 0;
		// Note: Map Matrixes indexes are in opposite order to C arrays. e.g. map matrix is indexed by (row, Col) which is (y, x) and c matrices are done by (x, y) which is (Col, Row)
        
        //for (int i = 0; i < nXSize; i++)
        //{
        //    for(int j = 0; j < nYSize; j++)
        //    {
        //        in_map->Get(j, i) = pafScanline[pafIterator];
        //        pafIterator++;
        //    }
        //}		
		for (int i = 0; i < nYSize; i++) //rows
		{
			for (int j = 0; j < nXSize; j++) //cols
			{
				in_map->Get(i, j) = pafScanline[pafIterator];
				pafIterator++;
			}
		}


    
    //free the c array storage
    delete pafScanline;
    int pbsuccess; // can be used with get no data value
    in_map->SetNoDataValue(poBand->GetNoDataValue(&pbsuccess));
    //This creates a list (map?) listing all the unique values contained in the raster.
	if (doCategorise) in_map->updateCategories();

    
	//Close GDAL, freeing the memory GDAL is using
	GDALClose( (GDALDatasetH)poDataset);

    return (std::make_tuple(in_map, projection, transformation));
}
Beispiel #8
0
int
prev_map(struct map *parm, int node)
{
    struct bitmap *map, *lowest;
    int bit, mask;
    int x, page;
    int best;
    int i;
    int bn;

#ifdef MAP_DEBUG
    if (Aflag) {
	printf("prev_map: selecting previous before %d from", node);
	print_map(parm);
    }
#endif
    if (NEGMAP(parm)) {
#ifdef MAP_DEBUG
	if (Aflag)
	    printf("prev_map failed; negative map\n");
#endif
	return -1;
    }

    if (node < 0)
	node = ((unsigned int)~0) >> 1;

    --node;
    bit = NUMBERTOBIT(node);
    x = NUMBERTOINDEX(node);
    page = NUMBERTOPAGE(node);
    bit = 1L << bit;
    best = -1;
    lowest = 0;
    for (map = MAP(parm); map; map = map->m_next)
	if (map->m_page <= page && (!lowest || lowest->m_page < map->m_page)) {
	    i = MDATA - 1;
	    mask = ~0;
	    if (page == map->m_page)
		i = x, mask = (bit << 1) - 1;
	    for (; i >= 0; --i, mask = ~0)
		if (map->m_data[i] & mask)
		    break;
	    if (i >= 0) {
		for (bn = (1 << LSHIFT) - 1; bn >= 0; --bn)
		    if (map->m_data[i] & mask & (1L << bn)) {
			break;
		    }
#ifdef MAP_DEBUG
		if (Aflag) {
		    if (bn < 0) {
			printf
			    ("prev_map: botch; pageno %d index %d data %#x mask %#x x,bit %d,%#x\n",
			     map->m_page, i, map->m_data[i], mask, x, bit);
			continue;
		    }
		}
#endif
		best = bn + ((i + ((map->m_page) << MSHIFT)
			     ) << LSHIFT);
		lowest = map;
	    }
	}
#ifdef MAP_DEBUG
    if (Aflag) {
	printf(" -> %d\n", best);
	if (best >= 0 && !in_map(parm, best)) {
	    printf("prev_map: botch; %d not in map\n", best);
	    return -1;
	}
    }
#endif
    return best;
}
Beispiel #9
0
int
next_map(struct map *parm, int node)
{
    struct bitmap *map, *lowest;
    int bit, mask;
    int x, page;
    int best;
    int i;
    int bn;

#ifdef MAP_DEBUG
    if (Aflag) {
	printf("next_map: selecting next after %d from", node);
	print_map(parm);
    }
#endif
    if (NEGMAP(parm)) {
#ifdef MAP_DEBUG
	if (Aflag)
	    printf("next_map failed; negative map\n");
#endif
	return -1;
    }

    ++node;
    bit = NUMBERTOBIT(node);
    x = NUMBERTOINDEX(node);
    page = NUMBERTOPAGE(node);
    bit = 1L << bit;
    best = -1;
    lowest = 0;
    for (map = MAP(parm); map; map = map->m_next)
	if (map->m_page >= page && (!lowest || lowest->m_page > map->m_page)) {
	    i = 0;
	    mask = ~0;
	    if (page == map->m_page)
		i = x, mask = -bit;
	    for (; i < MDATA; ++i, mask = ~0)
		if (map->m_data[i] & mask)
		    break;
	    if (i < MDATA) {
		for (bn = 0; bn < (1 << LSHIFT); ++bn)
		    if (map->m_data[i] & mask & (1L << bn)) {
			break;
		    }
#ifdef MAP_DEBUG
		if (Aflag) {
		    if (bn == (1 << LSHIFT)) {
			printf
			    ("next_map: botch; pageno %d index %d data %#x mask %#x x,bit %d,%#x\n",
			     map->m_page, i, map->m_data[i], mask, x, bit);
			continue;
		    }
		}
#endif
		best = bn + ((i + ((map->m_page) << MSHIFT)
			     ) << LSHIFT);
		lowest = map;
	    }
	}
#ifdef MAP_DEBUG
    if (Aflag) {
	printf(" -> %d\n", best);
	if (best >= 0 && !in_map(parm, best)) {
	    printf("next_map: botch; %d not in map\n", best);
	    return -1;
	}
    }
#endif
    return best;
}
Beispiel #10
0
int
main(int argc, char **argv)
{
   FILE *file;

   cons_CharsetEntry *cp = 0;

   int len = 0, i, mb = 0;

   char buf[4096];

   UniRecord *rp;

   /* unicode-order */
   Coll uni;

   /* charset-order */
   Coll cs;

   Coll out;

   Coll cmp;

   char *fname;

   if (argc < 2)
   {
      fprintf(stderr, "usage: %s charset_file [cs_file1...] < unicode_data\n", argv[0]);
      exit(1);
   }

   for (i = 1; i < argc; i++)
   {
      fname = argv[i];
      file = fopen(fname, "r");
      if (!file)
      {
	 fprintf(stderr, "cannot open %s: %s\n", fname, strerror(errno));
	 exit(2);
      }

      fprintf(stderr, "load charset '%s'\n", fname);
      if (load_charset(file, &cp, &len))
      {
	 fprintf(stderr, "cannot read %s: %s\n", fname, strerror(errno));
	 exit(3);
      }
      fprintf(stderr, "loaded %d entries\n", len);
      fclose(file);
#ifdef DBG
      fprintf(stderr, "readed %d charset entries\n", len);
#endif
   }

   init_Coll(&uni, 0, cmp_UniRecord);
   init_Coll(&cs, 0, cmp_CSRecord);
   init_Coll(&out, 0, 0);
   init_Coll(&cmp, 0, cmp_UniRecord);

   while (fgets(buf, sizeof(buf), stdin))
   {
      int l;

      char *s;

      rp = (UniRecord *) calloc(1, sizeof(*rp));
      l = strlen(buf);
      if (l > 0 && buf[--l] == '\n')
	 buf[l] = 0;
      if (!l)
	 break;

      s = strdup(buf);
		rp->mem_of_UniRecord = s;

		rp->hex_of_UniRecord = s;
		rp->no_of_UniRecord = strtoul(s, 0, 16);
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->name_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->cat_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->comb_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->bidir_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->decomp_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->dec_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->dig_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->num_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->mirror_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->name1_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->comment_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->upper_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->lower_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->title_of_UniRecord = s;
      l = strcspn(s, ";");
      s += l;
      *s++ = 0;

		rp->cp_of_UniRecord = in_map(cp, len, rp->no_of_UniRecord);
		if (rp->cp_of_UniRecord)
      {
			remove_char(&uni, rp->cp_of_UniRecord->ch_of_cons_CharsetEntry);
			remove_char(&cs, rp->cp_of_UniRecord->ch_of_cons_CharsetEntry);
	 insert_Coll(&uni, rp);
	 insert_Coll(&cs, rp);
      }
      else
      {
			free(rp->mem_of_UniRecord);
	 free(rp);
      }
   }
   fprintf(stderr, "appended %d uni %d chars\n", uni.count_of_Coll, cs.count_of_Coll);

#ifdef DBG
fprintf(stderr, "uni: %d\n", uni.count_of_Coll);
for (i = 0; i < uni.count_of_Coll; i++)
   {
      rp = (UniRecord *) uni.items[i];
		fprintf(stderr, "hex; 	'%s'\n", rp->hex_of_UniRecord);
		fprintf(stderr, "name;   '%s'\n", rp->name_of_UniRecord);
		fprintf(stderr, "cat;    '%s'\n", rp->cat_of_UniRecord);
		fprintf(stderr, "comb;   '%s'\n", rp->comb_of_UniRecord);
		fprintf(stderr, "bidir;  '%s'\n", rp->bidir_of_UniRecord);
		fprintf(stderr, "decomp; '%s'\n", rp->decomp_of_UniRecord);
		fprintf(stderr, "dec;    '%s'\n", rp->dec_of_UniRecord);
		fprintf(stderr, "dig;    '%s'\n", rp->dig_of_UniRecord);
		fprintf(stderr, "num;    '%s'\n", rp->num_of_UniRecord);
		fprintf(stderr, "mirror; '%s'\n", rp->mirror_of_UniRecord);
		fprintf(stderr, "name1;  '%s'\n", rp->name1_of_UniRecord);
		fprintf(stderr, "comment;'%s'\n", rp->comment_of_UniRecord);
		fprintf(stderr, "upper;  '%s'\n", rp->upper_of_UniRecord);
		fprintf(stderr, "lower;  '%s'\n", rp->lower_of_UniRecord);
		fprintf(stderr, "title;  '%s'\n", rp->title_of_UniRecord);
      fprintf(stderr, "\n");
   }
#endif
#ifdef DBG1
fprintf(stderr, "cs: %d\n", cs.count_of_Coll);
for (i = 0; i < cs.count_of_Coll; i++)
   {
      rp = (UniRecord *) cs.items[i];
		fprintf(stderr, "ch=%d\n", rp->cp_of_UniRecord->ch_of_cons_CharsetEntry);
		fprintf(stderr, "hex; 	'%s'\n", rp->hex_of_UniRecord);
		fprintf(stderr, "name;   '%s'\n", rp->name_of_UniRecord);
		fprintf(stderr, "cat;    '%s'\n", rp->cat_of_UniRecord);
		fprintf(stderr, "comb;   '%s'\n", rp->comb_of_UniRecord);
		fprintf(stderr, "bidir;  '%s'\n", rp->bidir_of_UniRecord);
		fprintf(stderr, "decomp; '%s'\n", rp->decomp_of_UniRecord);
		fprintf(stderr, "dec;    '%s'\n", rp->dec_of_UniRecord);
		fprintf(stderr, "dig;    '%s'\n", rp->dig_of_UniRecord);
		fprintf(stderr, "num;    '%s'\n", rp->num_of_UniRecord);
		fprintf(stderr, "mirror; '%s'\n", rp->mirror_of_UniRecord);
		fprintf(stderr, "name1;  '%s'\n", rp->name1_of_UniRecord);
		fprintf(stderr, "comment;'%s'\n", rp->comment_of_UniRecord);
		fprintf(stderr, "upper;  '%s'\n", rp->upper_of_UniRecord);
		fprintf(stderr, "lower;  '%s'\n", rp->lower_of_UniRecord);
		fprintf(stderr, "title;  '%s'\n", rp->title_of_UniRecord);
      fprintf(stderr, "\n");
   }
#endif

   for (i = 0; i < 256; i++)
   {
      UniRecord *rp = find_ch(&cs, i);

      if (!rp)
      {
	 cons_CharsetEntry *cp = (cons_CharsetEntry *) calloc(sizeof(cons_CharsetEntry *), 1);

	 rp = (UniRecord *) calloc(sizeof(UniRecord), 1);
	 rp->no_of_UniRecord = i;
	 rp->ch_of_UniRecord = i;
	 cp->ch_of_cons_CharsetEntry = i;
	 cp->unich_of_cons_CharsetEntry = i;
	 rp->cp_of_UniRecord = cp;
	 rp->hex_of_UniRecord = "";
	 rp->name_of_UniRecord = "";
	 rp->cat_of_UniRecord = "";
	 rp->comb_of_UniRecord = "";
	 rp->bidir_of_UniRecord = "";
	 rp->decomp_of_UniRecord = "";
	 rp->dec_of_UniRecord = "";
	 rp->dig_of_UniRecord = "";
	 rp->num_of_UniRecord = "";
	 rp->mirror_of_UniRecord = "";
	 rp->name1_of_UniRecord = "";
	 rp->comment_of_UniRecord = "";
	 rp->upper_of_UniRecord = "";
	 rp->lower_of_UniRecord = "";
	 rp->title_of_UniRecord = "";
      }
            if (rp->cp_of_UniRecord->ch_of_cons_CharsetEntry < 256)
      {
	 append_Coll(&out, rp);
	 insert_Coll(&cmp, rp);
      }
   }

#ifdef DBG3
fprintf(stderr, "cmp: %d\n", cmp.count_of_Coll);
for (i = 0; i < cmp.count_of_Coll; i++)
   {
		rp = (UniRecord *) cmp.items_of_Coll[i];
		fprintf(stderr, "ch=%d\n", rp->cp_of_UniRecord->ch_of_cons_CharsetEntry);
		fprintf(stderr, "hex; 	'%s'\n", rp->hex_of_UniRecord);
		fprintf(stderr, "name;   '%s'\n", rp->name_of_UniRecord);
		fprintf(stderr, "cat;    '%s'\n", rp->cat_of_UniRecord);
		fprintf(stderr, "comb;   '%s'\n", rp->comb_of_UniRecord);
		fprintf(stderr, "bidir;  '%s'\n", rp->bidir_of_UniRecord);
		fprintf(stderr, "decomp; '%s'\n", rp->decomp_of_UniRecord);
		fprintf(stderr, "dec;    '%s'\n", rp->dec_of_UniRecord);
		fprintf(stderr, "dig;    '%s'\n", rp->dig_of_UniRecord);
		fprintf(stderr, "num;    '%s'\n", rp->num_of_UniRecord);
		fprintf(stderr, "mirror; '%s'\n", rp->mirror_of_UniRecord);
		fprintf(stderr, "name1;  '%s'\n", rp->name1_of_UniRecord);
		fprintf(stderr, "comment;'%s'\n", rp->comment_of_UniRecord);
		fprintf(stderr, "upper;  '%s'\n", rp->upper_of_UniRecord);
		fprintf(stderr, "lower;  '%s'\n", rp->lower_of_UniRecord);
		fprintf(stderr, "title;  '%s'\n", rp->title_of_UniRecord);
      fprintf(stderr, "\n");
   }
#endif

   printf("# generated by gen_tbl from sources");
   for (i = 1; i < argc; i++)
      printf(" %s", argv[i]);
   printf("\n# cmptbl\n");
   for (i = 0; i < 256; i++)
   {
      int ch;

      ch = find_cmp(&cmp, i);
      printf("%d\n", ch);
   }
   printf("# uptbl\n");
	for (i = 0; i < out.count_of_Coll; i++)
   {
      UniRecord *rp1;

      int ch;

		rp = (UniRecord *) out.items_of_Coll[i];
      if (!rp)
      {
	 printf("%d\n", i);
	 continue;
      }
      if (!strcasecmp(rp->cat_of_UniRecord, "Ll") && rp->upper_of_UniRecord)
      {
			unsigned long unich = strtoul(rp->upper_of_UniRecord, 0, 16);

	 rp1 = find_uni(&uni, unich);
	 if (rp1)
		 ch = rp1->cp_of_UniRecord->ch_of_cons_CharsetEntry;
	 else
		 ch = rp->cp_of_UniRecord->ch_of_cons_CharsetEntry;
      }
      else
			ch = rp->cp_of_UniRecord->ch_of_cons_CharsetEntry;

      printf("%d\n", ch);
   }

   printf("# lowtbl\n");
	for (i = 0; i < out.count_of_Coll; i++)
   {
      UniRecord *rp1;

      int ch;

		rp = (UniRecord *) out.items_of_Coll[i];
      if (!rp)
      {
	 printf("%d\n", i);
	 continue;
      }
      if (!strcasecmp(rp->cat_of_UniRecord, "Lu") && rp->lower_of_UniRecord)
      {
			unsigned long unich = strtoul(rp->lower_of_UniRecord, 0, 16);

	 rp1 = find_uni(&uni, unich);
	 if (rp1)
		 ch = rp1->cp_of_UniRecord->ch_of_cons_CharsetEntry;
	 else
		 ch = rp->cp_of_UniRecord->ch_of_cons_CharsetEntry;
      }
      else
			ch = rp->cp_of_UniRecord->ch_of_cons_CharsetEntry;

      printf("%d\n", ch);
   }

   printf("# isalpha\n");
	for (i = 0; i < out.count_of_Coll; i++)
   {
      int r = 0;

      char *s;

		rp = (UniRecord *) out.items_of_Coll[i];
      if (!rp)
      {
	 printf("0\n");
	 continue;
      }
      s = rp->cat_of_UniRecord;
      if (s && s[0] == 'L')
	 r = 1;
      printf("%d\n", r);
   }

   printf("# pgtbl\n");
	for (i = 0; i < out.count_of_Coll; i++)
   {
      int r = 0;

      char *s;

		rp = (UniRecord *) out.items_of_Coll[i];
      if (!rp)
      {
	 printf("0\n");
	 continue;
      }
      s = rp->cat_of_UniRecord;
		if (!strcmp(s, "So") && rp->no_of_UniRecord >= 0x2500 && rp->no_of_UniRecord < 0x25ff)
			r = pg_chars[rp->no_of_UniRecord - 0x2500];
      printf("%d\n", r);
   }

   printf("# multibyte\n%d\n", mb ? 1 : 0);

   return 0;
}