예제 #1
0
static gpgme_error_t
parse_enc_to (char *args, gpgme_recipient_t *recp, gpgme_protocol_t protocol)
{
  gpgme_recipient_t rec;
  char *tail;
  int i;

  rec = malloc (sizeof (*rec));
  if (!rec)
    return gpg_error_from_syserror ();

  rec->next = NULL;
  rec->keyid = rec->_keyid;
  rec->status = 0;

  for (i = 0; i < sizeof (rec->_keyid) - 1; i++)
    {
      if (args[i] == '\0' || args[i] == ' ')
	break;

      rec->_keyid[i] = args[i];
    }
  rec->_keyid[i] = '\0';

  args = &args[i];
  if (*args != '\0' && *args != ' ')
    {
      free (rec);
      return trace_gpg_error (GPG_ERR_INV_ENGINE);
    }

  while (*args == ' ')
    args++;

  if (*args)
    {
      gpg_err_set_errno (0);
      rec->pubkey_algo = _gpgme_map_pk_algo (strtol (args, &tail, 0), protocol);
      if (errno || args == tail || *tail != ' ')
	{
	  /* The crypto backend does not behave.  */
	  free (rec);
	  return trace_gpg_error (GPG_ERR_INV_ENGINE);
	}
    }

  /* FIXME: The key length is always 0 right now, so no need to parse
     it.  */

  *recp = rec;
  return 0;
}
예제 #2
0
파일: verify.c 프로젝트: gpg/gpgme
static gpgme_error_t
parse_valid_sig (gpgme_signature_t sig, char *args, gpgme_protocol_t protocol)
{
  char *end = strchr (args, ' ');
  if (end)
    {
      *end = '\0';
      end++;
    }

  if (!*args)
    /* We require at least the fingerprint.  */
    return gpg_error (GPG_ERR_GENERAL);

  if (sig->fpr)
    free (sig->fpr);
  sig->fpr = strdup (args);
  if (!sig->fpr)
    return gpg_error_from_syserror ();

  /* Skip the creation date.  */
  end = strchr (end, ' ');
  if (end)
    {
      char *tail;

      sig->timestamp = _gpgme_parse_timestamp (end, &tail);
      if (sig->timestamp == -1 || end == tail || (*tail && *tail != ' '))
	return trace_gpg_error (GPG_ERR_INV_ENGINE);
      end = tail;

      sig->exp_timestamp = _gpgme_parse_timestamp (end, &tail);
      if (sig->exp_timestamp == -1 || end == tail || (*tail && *tail != ' '))
	return trace_gpg_error (GPG_ERR_INV_ENGINE);
      end = tail;

      while (*end == ' ')
	end++;
      /* Skip the signature version.  */
      end = strchr (end, ' ');
      if (end)
	{
	  while (*end == ' ')
	    end++;

	  /* Skip the reserved field.  */
	  end = strchr (end, ' ');
	  if (end)
	    {
	      /* Parse the pubkey algo.  */
	      gpg_err_set_errno (0);
	      sig->pubkey_algo = _gpgme_map_pk_algo (strtol (end, &tail, 0),
                                                     protocol);
	      if (errno || end == tail || *tail != ' ')
		return trace_gpg_error (GPG_ERR_INV_ENGINE);
	      end = tail;

	      while (*end == ' ')
		end++;

	      if (*end)
		{
		  /* Parse the hash algo.  */

		  gpg_err_set_errno (0);
		  sig->hash_algo = strtol (end, &tail, 0);
		  if (errno || end == tail || *tail != ' ')
		    return trace_gpg_error (GPG_ERR_INV_ENGINE);
		  end = tail;
		}
	    }
	}
    }
  return 0;
}
예제 #3
0
파일: verify.c 프로젝트: gpg/gpgme
static gpgme_error_t
parse_new_sig (op_data_t opd, gpgme_status_code_t code, char *args,
               gpgme_protocol_t protocol)
{
  gpgme_signature_t sig;
  char *end = strchr (args, ' ');
  char *tail;

  if (end)
    {
      *end = '\0';
      end++;
    }

  if (!opd->did_prepare_new_sig)
    {
      gpg_error_t err;

      err = prepare_new_sig (opd);
      if (err)
        return err;
    }
  assert (opd->did_prepare_new_sig);
  opd->did_prepare_new_sig = 0;

  assert (opd->current_sig);
  sig = opd->current_sig;

  /* FIXME: We should set the source of the state.  */
  switch (code)
    {
    case GPGME_STATUS_GOODSIG:
      sig->status = gpg_error (GPG_ERR_NO_ERROR);
      break;

    case GPGME_STATUS_EXPSIG:
      sig->status = gpg_error (GPG_ERR_SIG_EXPIRED);
      break;

    case GPGME_STATUS_EXPKEYSIG:
      sig->status = gpg_error (GPG_ERR_KEY_EXPIRED);
      break;

    case GPGME_STATUS_BADSIG:
      sig->status = gpg_error (GPG_ERR_BAD_SIGNATURE);
      break;

    case GPGME_STATUS_REVKEYSIG:
      sig->status = gpg_error (GPG_ERR_CERT_REVOKED);
      break;

    case GPGME_STATUS_ERRSIG:
      /* Parse the pubkey algo.  */
      if (!end)
	goto parse_err_sig_fail;
      gpg_err_set_errno (0);
      sig->pubkey_algo = _gpgme_map_pk_algo (strtol (end, &tail, 0), protocol);
      if (errno || end == tail || *tail != ' ')
	goto parse_err_sig_fail;
      end = tail;
      while (*end == ' ')
	end++;

      /* Parse the hash algo.  */
      if (!*end)
	goto parse_err_sig_fail;
      gpg_err_set_errno (0);
      sig->hash_algo = strtol (end, &tail, 0);
      if (errno || end == tail || *tail != ' ')
	goto parse_err_sig_fail;
      end = tail;
      while (*end == ' ')
	end++;

      /* Skip the sig class.  */
      end = strchr (end, ' ');
      if (!end)
	goto parse_err_sig_fail;
      while (*end == ' ')
	end++;

      /* Parse the timestamp.  */
      sig->timestamp = _gpgme_parse_timestamp (end, &tail);
      if (sig->timestamp == -1 || end == tail || (*tail && *tail != ' '))
	return trace_gpg_error (GPG_ERR_INV_ENGINE);
      end = tail;
      while (*end == ' ')
	end++;

      /* Parse the return code.  */
      if (end[0] && (!end[1] || end[1] == ' '))
	{
	  switch (end[0])
	    {
	    case '4':
	      sig->status = gpg_error (GPG_ERR_UNSUPPORTED_ALGORITHM);
	      break;

	    case '9':
	      sig->status = gpg_error (GPG_ERR_NO_PUBKEY);
	      break;

	    default:
	      sig->status = gpg_error (GPG_ERR_GENERAL);
	    }
	}
      else
	goto parse_err_sig_fail;

      goto parse_err_sig_ok;

    parse_err_sig_fail:
      sig->status = gpg_error (GPG_ERR_GENERAL);
    parse_err_sig_ok:
      break;

    default:
      return gpg_error (GPG_ERR_GENERAL);
    }

  if (*args)
    {
      sig->fpr = strdup (args);
      if (!sig->fpr)
	return gpg_error_from_syserror ();
    }
  return 0;
}