コード例 #1
0
ファイル: parse.c プロジェクト: bennoleslie/pkg-config
static void
parse_line (Package *pkg, const char *untrimmed, const char *path,
	    gboolean ignore_requires, gboolean ignore_private_libs,
	    gboolean ignore_requires_private)
{
  char *str;
  char *p;
  char *tag;

  debug_spew ("  line>%s\n", untrimmed);
  
  str = trim_string (untrimmed);
  
  if (*str == '\0') /* empty line */
    {
      g_free(str);
      return;
    }
  
  p = str;

  /* Get first word */
  while ((*p >= 'A' && *p <= 'Z') ||
	 (*p >= 'a' && *p <= 'z') ||
	 (*p >= '0' && *p <= '9') ||
	 *p == '_' || *p == '.')
    p++;

  tag = g_strndup (str, p - str);
  
  while (*p && isspace ((guchar)*p))
    ++p;

  if (*p == ':')
    {
      /* keyword */
      ++p;
      while (*p && isspace ((guchar)*p))
        ++p;

      if (strcmp (tag, "Name") == 0)
        parse_name (pkg, p, path);
      else if (strcmp (tag, "Description") == 0)
        parse_description (pkg, p, path);
      else if (strcmp (tag, "Version") == 0)
        parse_version (pkg, p, path);
      else if (strcmp (tag, "Requires.private") == 0)
	{
	  if (!ignore_requires_private)
	    parse_requires_private (pkg, p, path);
	}
      else if (strcmp (tag, "Requires") == 0)
	{
          if (ignore_requires == FALSE)
	    parse_requires (pkg, p, path);
          else
	    goto cleanup;
        }
      else if ((strcmp (tag, "Libs.private") == 0) && 
               ignore_private_libs == FALSE)
        parse_libs_private (pkg, p, path);
      else if (strcmp (tag, "Libs") == 0)
        parse_libs (pkg, p, path);
      else if (strcmp (tag, "Cflags") == 0 ||
               strcmp (tag, "CFlags") == 0)
        parse_cflags (pkg, p, path);
      else if (strcmp (tag, "Conflicts") == 0)
        parse_conflicts (pkg, p, path);
      else if (strcmp (tag, "URL") == 0)
        parse_url (pkg, p, path);
      else
        {
	  /* we don't error out on unknown keywords because they may
	   * represent additions to the .pc file format from future
	   * versions of pkg-config.  We do make a note of them in the
	   * debug spew though, in order to help catch mistakes in .pc
	   * files. */
          debug_spew ("Unknown keyword '%s' in '%s'\n",
		      tag, path);
        }
    }
  else if (*p == '=')
    {
      /* variable */
      char *varname;
      char *varval;
      
      ++p;
      while (*p && isspace ((guchar)*p))
        ++p;
      
      if (pkg->vars == NULL)
        pkg->vars = g_hash_table_new (g_str_hash, g_str_equal);

#ifdef G_OS_WIN32
      if (!dont_define_prefix && strcmp (tag, prefix_variable) == 0)
	{
	  /* This is the prefix variable. Try to guesstimate a value for it
	   * for this package from the location of the .pc file.
	   */

	  gchar *prefix = pkg->pcfiledir;
	  const int prefix_len = strlen (prefix);
	  const char *const lib_pkgconfig = "\\lib\\pkgconfig";
	  const char *const share_pkgconfig = "\\share\\pkgconfig";
	  const int lib_pkgconfig_len = strlen (lib_pkgconfig);
	  const int share_pkgconfig_len = strlen (share_pkgconfig);

	  if ((strlen (prefix) > lib_pkgconfig_len &&
	       pathnamecmp (prefix + prefix_len - lib_pkgconfig_len, lib_pkgconfig) == 0) ||
	      (strlen (prefix) > share_pkgconfig_len &&
	       pathnamecmp (prefix + prefix_len - share_pkgconfig_len, share_pkgconfig) == 0))
	    {
	      /* It ends in lib\pkgconfig or share\pkgconfig. Good. */
	      
	      gchar *q;
	      
	      orig_prefix = g_strdup (p);

	      prefix = g_strdup (prefix);
	      if (strlen (prefix) > lib_pkgconfig_len &&
		  pathnamecmp (prefix + prefix_len - lib_pkgconfig_len, lib_pkgconfig) == 0)
		prefix[prefix_len - lib_pkgconfig_len] = '\0';
	      else
		prefix[prefix_len - share_pkgconfig_len] = '\0';
	      
	      /* Turn backslashes into slashes or
	       * poptParseArgvString() will eat them when ${prefix}
	       * has been expanded in parse_libs().
	       */
	      q = prefix;
	      while (*q)
		{
		  if (*q == '\\')
		    *q = '/';
		  q++;
		}
	      varname = g_strdup (tag);
	      debug_spew (" Variable declaration, '%s' overridden with '%s'\n",
			  tag, prefix);
	      g_hash_table_insert (pkg->vars, varname, prefix);
	      goto cleanup;
	    }
	}
      else if (!dont_define_prefix &&
	       orig_prefix != NULL &&
	       strncmp (p, orig_prefix, strlen (orig_prefix)) == 0 &&
	       G_IS_DIR_SEPARATOR (p[strlen (orig_prefix)]))
	{
	  char *oldstr = str;

	  p = str = g_strconcat (g_hash_table_lookup (pkg->vars, prefix_variable), p + strlen (orig_prefix), NULL);
	  g_free (oldstr);
	}
#endif

      if (g_hash_table_lookup (pkg->vars, tag))
        {
          verbose_error ("Duplicate definition of variable '%s' in '%s'\n",
                         tag, path);

          exit (1);
        }

      varname = g_strdup (tag);
      varval = trim_and_sub (pkg, p, path);     

      debug_spew (" Variable declaration, '%s' has value '%s'\n",
                  varname, varval);
      g_hash_table_insert (pkg->vars, varname, varval);
  
    }

 cleanup:  
  g_free (str);
  g_free (tag);
}
コード例 #2
0
ファイル: parse.c プロジェクト: DeepthiGumpula/WatirRuby
Package *
get_compat_package (const char *name)
{
#ifdef G_OS_WIN32
  /* There has never been any of these legacy *-config scripts on
   * Windows as far as I know. No use trying to execute them, will
   * only confuse users to see the "blabla is not recognized as an
   * internal or external command, operable program or batch file"
   * messages.
   */
  return NULL;
#else

  Package *pkg;

  if (name_ends_in_uninstalled (name))
    debug_spew ("Suspiciously looking for compat package for -uninstalled: %s\n", name);
  
  debug_spew ("Looking for '%s' using legacy -config scripts\n", name);
  
  pkg = g_new0 (Package, 1);

  pkg->path_position = G_MAXINT;
  
  if (strcmp (name, "glib") == 0)
    {
      char *output;

      debug_spew ("Calling glib-config\n");
      
      pkg->version = backticks ("glib-config --version");
      if (pkg->version == NULL)
        {
          g_free (pkg);
          return NULL;
        }
      
      pkg->name = g_strdup ("GLib");
      pkg->key = g_strdup ("glib");
      pkg->description = g_strdup ("C Utility Library");

      output = backticks ("glib-config --libs");
      parse_libs (pkg, output, "glib-config");
      g_free (output);

      output = backticks ("glib-config --cflags");
      parse_cflags (pkg, output, "glib-config");
      g_free (output);

      return pkg;
    }
  else if (strcmp (name, "gtk+") == 0)
    {
      char *output;

      debug_spew ("Calling gtk-config\n");
      
      pkg->version = backticks ("gtk-config --version");
      if (pkg->version == NULL)
        {
          g_free (pkg);
          return NULL;
        }
      
      pkg->name = g_strdup ("GTK+");
      pkg->key = g_strdup ("gtk+");
      pkg->description = g_strdup ("GIMP Tool Kit");

      output = backticks ("gtk-config --libs");
      parse_libs (pkg, output, "gtk-config");
      g_free (output);

      output = backticks ("gtk-config --cflags");
      parse_cflags (pkg, output, "gtk-config");
      g_free (output);

      return pkg;
    }
  else if (strcmp (name, "libgnomevfs") == 0)
    {
      char *output;

      debug_spew ("Calling gnome-vfs-config\n");
      
      pkg->version = backticks ("gnome-vfs-config --version");
      if (pkg->version == NULL)
        {
          g_free (pkg);
          return NULL;
        }
      
      pkg->name = g_strdup ("GNOME VFS");
      pkg->key = g_strdup ("libgnomevfs");
      pkg->description = g_strdup ("GNOME Virtual File System");

      output = backticks ("gnome-vfs-config --libs");
      parse_libs (pkg, output, "gnome-vfs-config");
      g_free (output);

      output = backticks ("gnome-vfs-config --cflags");
      parse_cflags (pkg, output, "gnome-vfs-config");
      g_free (output);

      return pkg;
    }
  else if (strcmp (name, "imlib") == 0)
    {
      char *output;

      debug_spew ("Calling imlib-config\n");
      
      pkg->version = backticks ("imlib-config --version");
      if (pkg->version == NULL)
        {
          g_free (pkg);
          return NULL;
        }
      
      pkg->name = g_strdup ("Imlib");
      pkg->key = g_strdup ("imlib");
      pkg->description = g_strdup ("Imlib image loading library");

      output = backticks ("imlib-config --libs-gdk");
      parse_libs (pkg, output, "imlib-config");
      g_free (output);

      output = backticks ("imlib-config --cflags-gdk");
      parse_cflags (pkg, output, "imlib-config");
      g_free (output);

      return pkg;
    }
  else if (strcmp (name, "orbit-client") == 0)
    {
      char *output;
      char *p;

      debug_spew ("Calling orbit-config\n");
      
      output = backticks ("orbit-config --version");
      
      if (output == NULL)
        {
          g_free (pkg);
          return NULL;
        }

      p = output;

      while (*p && isspace ((guchar)*p))
        ++p;

      if (*p == '\0')
        {
          /* empty output */
          g_free (output);
          g_free (pkg);
          return NULL;
        }

      /* only heuristic; find a number or . */
      while (*p && ! (isdigit ((guchar)*p) || *p == '.'))
        ++p;      

      pkg->version = g_strdup (p);

      g_free (output);
      
      pkg->name = g_strdup ("ORBit Client");
      pkg->key = g_strdup ("orbit-client");
      pkg->description = g_strdup ("ORBit Client Libraries");

      output = backticks ("orbit-config --libs client");
      parse_libs (pkg, output, "orbit-config");
      g_free (output);

      output = backticks ("orbit-config --cflags client");
      parse_cflags (pkg, output, "orbit-config");
      g_free (output);

      return pkg;
    }
  else if (strcmp (name, "orbit-server") == 0)
    {
      char *output;
      char *p;

      debug_spew ("Calling orbit-config\n");
      
      output = backticks ("orbit-config --version");
      
      if (output == NULL)
        {
          g_free (pkg);
          return NULL;
        }

      p = output;

      while (*p && isspace ((guchar)*p))
        ++p;

      if (*p == '\0')
        {
          /* empty output */
          g_free (output);
          g_free (pkg);
          return NULL;
        }

      /* only heuristic; find a number or . */
      while (*p && ! (isdigit ((guchar)*p) || *p == '.'))
        ++p;      

      pkg->version = g_strdup (p);

      g_free (output);
      
      pkg->name = g_strdup ("ORBit Server");
      pkg->key = g_strdup ("orbit-server");
      pkg->description = g_strdup ("ORBit Server Libraries");

      output = backticks ("orbit-config --libs server");
      parse_libs (pkg, output, "orbit-config");
      g_free (output);

      output = backticks ("orbit-config --cflags server");
      parse_cflags (pkg, output, "orbit-config");
      g_free (output);

      return pkg;
    }
  else
    {
      /* Check for the module in gnome-config */
      char *output;
      char *p;
      char *command;

      debug_spew ("Calling gnome-config\n");
      
      /* Annoyingly, --modversion doesn't return a failure
       * code if the lib is unknown, so we have to use --libs
       * for that.
       */
      
      command = g_strdup_printf ("gnome-config --libs %s",
                                 name);
      
      if (!try_command (command))
        {
          g_free (command);
          g_free (pkg);
          return NULL;
        }
      else
        g_free (command);
      
      command = g_strdup_printf ("gnome-config --modversion %s",
                                 name);
      
      output = backticks (command);
      g_free (command);
      if (output == NULL)
        {
          g_free (pkg);
          return NULL;
        }
      
      /* Unknown modules give "Unknown library `foo'" from gnome-config
       * (but on stderr so this is useless, nevermind)
       */
      if (strstr (output, "Unknown") || *output == '\0')
        {
          g_free (output);
          g_free (pkg);
          return NULL;
        }

      /* gnome-config --modversion gnomeui outputs e.g. "gnome-libs-1.2.4"
       * or libglade-0.12
       */
      p = output;

      while (*p && isspace ((guchar)*p))
        ++p;

      if (*p == '\0')
        {
          /* empty output */
          g_free (output);
          g_free (pkg);
          return NULL;
        }

      /* only heuristic; find a number or . */
      while (*p && ! (isdigit ((guchar)*p) || *p == '.'))
        ++p;      

      pkg->version = g_strdup (p);

      g_free (output);
      
      /* Strip newline */
      p = pkg->version;
      while (*p)
        {
          if (*p == '\n')
            *p = '\0';

          ++p;
        }
      
      pkg->name = g_strdup (name);
      pkg->key = g_strdup (name);
      pkg->description = g_strdup ("No description");

      command = g_strdup_printf ("gnome-config --libs %s", name);
      output = backticks (command);
      g_free (command);
      parse_libs (pkg, output, "gnome-config");
      g_free (output);

      command = g_strdup_printf ("gnome-config --cflags %s", name);
      output = backticks (command);
      g_free (command);
      parse_cflags (pkg, output, "gnome-config");
      g_free (output);

      return pkg;
    }
#endif
}