Пример #1
0
int
main (int argc, char **argv)
{
    GIOChannel *channel;
    GIOStatus status;
    GError *error;
    gchar *line = NULL;
    gsize length, terminator_pos;
    FriBidiStrIndex *expected_ltor = NULL;
    FriBidiStrIndex expected_ltor_len = 0;
    FriBidiStrIndex *ltor = NULL;
    FriBidiStrIndex ltor_len = 0;
    FriBidiCharType *types = NULL;
    FriBidiStrIndex types_len = 0;
    FriBidiLevel *expected_levels = NULL;
    FriBidiLevel expected_levels_len = 0;
    FriBidiLevel *levels = NULL;
    FriBidiStrIndex levels_len = 0;
    int base_dir_flags, base_dir_mode;
    int numerrs = 0;
    int numtests = 0;
    int line_no = 0;
    gboolean debug = FALSE;
    const char *filename;
    int next_arg;

    if (argc < 2) {
	g_printerr ("usage: %s [--debug] test-file-name\n", argv[0]);
	exit (1);
    }

    next_arg = 1;
    if (!strcmp (argv[next_arg], "--debug")) {
	debug = TRUE;
	next_arg++;
    }

    filename = argv[next_arg++];

    error = NULL;
    channel = g_io_channel_new_file (filename, "r", &error);
    if (!channel) {
	g_printerr ("%s\n", error->message);
	exit (1);
    }

    while (TRUE) {
	error = NULL;
	g_free (line);
	status = g_io_channel_read_line (channel, &line, &length, &terminator_pos, &error);
	switch (status) {
        case G_IO_STATUS_ERROR:
            g_printerr ("%s\n", error->message);
            exit (1);

        case G_IO_STATUS_EOF:
	    goto done;

        case G_IO_STATUS_AGAIN:
            continue;

        case G_IO_STATUS_NORMAL:
            line[terminator_pos] = '\0';
            break;
	}

	line_no++;

	if (line[0] == '#' || line[0] == '\0')
	    continue;

	if (line[0] == '@')
	{
	    if (!strncmp (line, "@Reorder:", 9)) {
		g_free (expected_ltor);
		expected_ltor = parse_reorder_line (line, &expected_ltor_len);
		continue;
	    }
	    if (!strncmp (line, "@Levels:", 8)) {
		g_free (expected_levels);
		expected_levels = parse_levels_line (line, &expected_levels_len);
		continue;
	    }
	    continue;
	}

	/* Test line */
	g_free (types);
	types = parse_test_line (line, &types_len, &base_dir_flags);

	g_free (levels);
	levels = g_malloc (sizeof (FriBidiLevel) * types_len);
	levels_len = types_len;

	g_free (ltor);
	ltor = g_malloc (sizeof (FriBidiStrIndex) * types_len);

	/* Test it */
	for (base_dir_mode = 0; base_dir_mode < 3; base_dir_mode++) {
	    FriBidiParType base_dir;
	    int i, j;
	    gboolean matches;

	    if ((base_dir_flags & (1<<base_dir_mode)) == 0)
		continue;

            numtests++;

	    switch (base_dir_mode) {
	    case 0: base_dir = FRIBIDI_PAR_ON;  break;
	    case 1: base_dir = FRIBIDI_PAR_LTR; break;
	    case 2: base_dir = FRIBIDI_PAR_RTL; break;
	    }

	    fribidi_get_par_embedding_levels (types, types_len,
					      &base_dir,
					      levels);

	    for (i = 0; i < types_len; i++)
	        ltor[i] = i;

	    fribidi_reorder_line (0 /*FRIBIDI_FLAG_REORDER_NSM*/,
				  types, types_len,
				  0, base_dir,
				  levels,
				  NULL,
				  ltor);

	    j = 0;
	    for (i = 0; i < types_len; i++)
	    	if (!FRIBIDI_IS_EXPLICIT_OR_BN (types[ltor[i]]))
		    ltor[j++] = ltor[i];
	    ltor_len = j;

	    /* Compare */
	    matches = TRUE;
	    if (levels_len != expected_levels_len)
		matches = FALSE;
	    if (matches)
		for (i = 0; i < levels_len; i++)
		    if (levels[i] != expected_levels[i] &&
			expected_levels[i] != (FriBidiLevel) -1) {
			matches = FALSE;
			break;
		    }

	    if (ltor_len != expected_ltor_len)
		matches = FALSE;
	    if (matches)
		for (i = 0; i < ltor_len; i++)
		    if (ltor[i] != expected_ltor[i]) {
			matches = FALSE;
			break;
		    }

	    if (!matches)
	    {
		numerrs++;

		g_printerr ("failure on line %d\n", line_no);
		g_printerr ("input is: %s\n", line);
		g_printerr ("base dir: %s\n", base_dir_mode==0 ? "auto"
					    : base_dir_mode==1 ? "LTR" : "RTL");

		g_printerr ("expected levels:");
		for (i = 0; i < expected_levels_len; i++)
		    if (expected_levels[i] == (FriBidiLevel) -1)
			g_printerr (" x");
		    else
			g_printerr (" %d", expected_levels[i]);
		g_printerr ("\n");
		g_printerr ("returned levels:");
		for (i = 0; i < levels_len; i++)
		    g_printerr (" %d", levels[i]);
		g_printerr ("\n");

		g_printerr ("expected order:");
		for (i = 0; i < expected_ltor_len; i++)
		    g_printerr (" %d", expected_ltor[i]);
		g_printerr ("\n");
		g_printerr ("returned order:");
		for (i = 0; i < ltor_len; i++)
		    g_printerr (" %d", ltor[i]);
		g_printerr ("\n");

		if (debug) {
		    FriBidiParType base_dir;

		    fribidi_set_debug (1);

		    switch (base_dir_mode) {
		    case 0: base_dir = FRIBIDI_PAR_ON;  break;
		    case 1: base_dir = FRIBIDI_PAR_LTR; break;
		    case 2: base_dir = FRIBIDI_PAR_RTL; break;
		    }

		    fribidi_get_par_embedding_levels (types, types_len,
						      &base_dir,
						      levels);

		    fribidi_set_debug (0);
		}

		g_printerr ("\n");
	    }
	}
    }

done:
    g_free (ltor);
    g_free (levels);
    g_free (expected_ltor);
    g_free (types);
    g_free (line);
    g_io_channel_unref (channel);
    if (error)
	g_error_free (error);

    if (numerrs)
	g_printerr ("%d errors out of %d total tests\n", numerrs, numtests);
    return numerrs;
}
Пример #2
0
int
main (int argc, char **argv)
{
  GError *error;
  int next_arg;
  GIOChannel *channel;
  GIOStatus status;
  const char *filename;
  gchar *line = NULL;
  gsize length, terminator_pos;
  int numerrs = 0;
  int line_no = 0;
  FriBidiChar *code_points = NULL;
  int code_points_len = 0;
  int expected_ltor_len = 0;
  int base_dir_mode = 0, paragraph_dir;
  FriBidiLevel *expected_levels = NULL;
  int *expected_ltor = NULL;
  int resolved_paragraph_embedding_level;
  FriBidiLevel *levels = NULL;
  FriBidiCharType *types = NULL;
  FriBidiBracketType *bracket_types = NULL;
  FriBidiStrIndex *ltor = NULL;
  int ltor_len;
  gboolean debug = FALSE;

  if (argc < 2)
    {
      g_printerr ("usage: %s [--debug] test-file-name\n", argv[0]);
      exit (1);
    }

  next_arg = 1;
  while(next_arg < argc && argv[next_arg][0]=='-')
    {
      const char *arg = argv[next_arg++];
      if (strcmp(arg, "--debug")==0)
        {
          debug=TRUE;
          continue;
        }
      die("Unknown option %s!\n", arg);
    }
  
  filename = argv[next_arg++];

  error = NULL;
  channel = g_io_channel_new_file (filename, "r", &error);
  if (!channel)
    {
      g_printerr ("%s\n", error->message);
      exit (1);
    }

  fribidi_set_debug(debug);

  while (TRUE)
    {
      error = NULL;
      g_free (line);
      status = g_io_channel_read_line (channel, &line, &length, &terminator_pos, &error);
      switch (status)
        {
        case G_IO_STATUS_ERROR:
          g_printerr ("%s\n", error->message);
          exit (1);

        case G_IO_STATUS_EOF:
          goto done;

        case G_IO_STATUS_AGAIN:
          continue;

        case G_IO_STATUS_NORMAL:
          line[terminator_pos] = '\0';
          break;
	}

      line_no++;

      if (line[0] == '#' || line[0] == '\0')
        continue;

      parse_test_line (line,
                       line_no,
                       &code_points,      /* Field 0 */
                       &code_points_len,
                       &paragraph_dir,    /* Field 1 */
                       &resolved_paragraph_embedding_level,   /* Field 2 */
                       &expected_levels,   /* Field 3 */
                       &expected_ltor,    /* Field 4 */
                       &expected_ltor_len
                       );

      /* Test it */
      g_free(bracket_types);
      bracket_types = g_malloc ( sizeof(FriBidiBracketType) * code_points_len);

      g_free(types);
      types = g_malloc ( sizeof(FriBidiCharType) * code_points_len);

      g_free(levels);
      levels = g_malloc (sizeof (FriBidiLevel) * code_points_len);

      g_free (ltor);
      ltor = g_malloc (sizeof (FriBidiStrIndex) * code_points_len);


      {
        FriBidiParType base_dir;
        int i, j;
        gboolean matches;
        int types_len = code_points_len;
        int levels_len = types_len;
        FriBidiBracketType NoBracket = FRIBIDI_NO_BRACKET;

        for (i=0; i<code_points_len; i++)
          {
            types[i] = fribidi_get_bidi_type(code_points[i]);

            /* Note the optimization that a bracket is always
               of type neutral */
            if (types[i] == FRIBIDI_TYPE_ON)
                bracket_types[i] = fribidi_get_bracket(code_points[i]);
            else
                bracket_types[i] = NoBracket;
          }

        if ((paragraph_dir & (1<<base_dir_mode)) == 0)
          continue;

        switch (paragraph_dir)
          {
          case 0: base_dir = FRIBIDI_PAR_LTR; break;
          case 1: base_dir = FRIBIDI_PAR_RTL; break;
          case 2: base_dir = FRIBIDI_PAR_ON;  break;
          }

        if (fribidi_get_par_embedding_levels_ex (types,
                                                 bracket_types,
                                                 types_len,
                                                 &base_dir,
                                                 levels))
            ;

        for (i = 0; i < types_len; i++)
          ltor[i] = i;

        if (fribidi_reorder_line (0 /*FRIBIDI_FLAG_REORDER_NSM*/,
                                  types, types_len,
                                  0, base_dir,
                                  levels,
                                  NULL,
                                  ltor))
            ;

        j = 0;
        for (i = 0; i < types_len; i++)
          if (!FRIBIDI_IS_EXPLICIT_OR_BN (types[ltor[i]]))
            ltor[j++] = ltor[i];
        ltor_len = j;

        /* Compare */
        matches = TRUE;
        if (matches)
          for (i = 0; i < code_points_len; i++)
            if (levels[i] != expected_levels[i] &&
                expected_levels[i] != (FriBidiLevel) -1) {
              matches = FALSE;
              break;
            }

        if (ltor_len != expected_ltor_len)
          matches = FALSE;
        if (matches)
          for (i = 0; i < ltor_len; i++)
            if (ltor[i] != expected_ltor[i]) {
              matches = FALSE;
              break;
            }

        if (!matches)
          {
            numerrs++;

            g_printerr ("failure on line %d\n", line_no);
            g_printerr ("input is: %s\n", line);
            g_printerr ("base dir: %s\n", paragraph_dir==0 ? "LTR"
                        : paragraph_dir==1 ? "RTL" : "AUTO");

            g_printerr ("expected levels:");
            for (i = 0; i < code_points_len; i++)
              if (expected_levels[i] == (FriBidiLevel) -1)
                g_printerr (" x");
              else
                g_printerr (" %d", expected_levels[i]);
            g_printerr ("\n");
            g_printerr ("returned levels:");
            for (i = 0; i < levels_len; i++)
              g_printerr (" %d", levels[i]);
            g_printerr ("\n");

            g_printerr ("expected order:");
            for (i = 0; i < expected_ltor_len; i++)
              g_printerr (" %d", expected_ltor[i]);
            g_printerr ("\n");
            g_printerr ("returned order:");
            for (i = 0; i < ltor_len; i++)
              g_printerr (" %d", ltor[i]);
            g_printerr ("\n");

            if (debug)
              {
                FriBidiParType base_dir;

                fribidi_set_debug (1);

                switch (base_dir_mode)
                  {
                  case 0: base_dir = FRIBIDI_PAR_ON;  break;
                  case 1: base_dir = FRIBIDI_PAR_LTR; break;
                  case 2: base_dir = FRIBIDI_PAR_RTL; break;
                  }

                if (fribidi_get_par_embedding_levels_ex (types,
                                                         bracket_types,
                                                         types_len,
                                                         &base_dir,
                                                         levels))
                    ;

                fribidi_set_debug (0);
              }

            g_printerr ("\n");
          }
      }
    }

done:
  if (error)
    g_error_free (error);

  if (numerrs)
    g_printerr ("%d errors\n", numerrs);
  else
    printf("No errors found! :-)\n");

  return numerrs;
}