Gather up another utility.
[u/mdw/catacomb] / key-text.c
index 393fbd9..dcfe354 100644 (file)
@@ -1,6 +1,6 @@
 /* -*-c-*-
  *
- * $Id: key-text.c,v 1.2 2000/06/17 11:27:20 mdw Exp $
+ * $Id: key-text.c,v 1.6 2004/04/08 01:36:15 mdw Exp $
  *
  * Key textual encoding
  *
  * MA 02111-1307, USA.
  */
 
-/*----- Revision history --------------------------------------------------* 
- *
- * $Log: key-text.c,v $
- * Revision 1.2  2000/06/17 11:27:20  mdw
- * Use secure memory interface from MP library.
- *
- * Revision 1.1  2000/02/12 18:21:02  mdw
- * Overhaul of key management (again).
- *
- */
-
 /*----- Header files ------------------------------------------------------*/
 
+#include <ctype.h>
 #include <stdlib.h>
 #include <string.h>
 
@@ -48,6 +38,7 @@
 #include <mLib/dstr.h>
 #include <mLib/sub.h>
 #include <mLib/sym.h>
+#include <mLib/url.h>
 
 #include "key-data.h"
 #include "mp.h"
@@ -127,6 +118,51 @@ int key_read(const char *p, key_data *k, char **pp)
       p = q;
     } break;
 
+    /* --- String encoding --- *
+     *
+     * We use form-urlencoding to ensure that evil characters don't get out.
+     */
+
+    case KENC_STRING: {
+      dstr d = DSTR_INIT;
+      size_t sz = strcspn(p, ",]");
+      const char *l = p + sz;
+      unsigned int ch;
+      int x, n;
+
+      while (p < l) {
+       switch (*p) {
+         case '+':
+           DPUTC(&d, ' '); break;
+         case '%':
+           x = sscanf(p + 1, "%2x%n", &ch, &n);
+           if (x == 1) { DPUTC(&d, ch); p += n; break; }
+         default:
+           DPUTC(&d, *p); break;
+       }
+       p++;
+      }
+      DPUTZ(&d);
+      k->u.p = xstrdup(d.buf);
+      dstr_destroy(&d);
+    } break;
+
+    /* --- Elliptic curve encoding --- *
+     *
+     * Again, we have a convenient function.  Assume for now that points
+     * aren't secret.  (Reasonably safe.)
+     */
+
+    case KENC_EC: {
+      qd_parse qd;
+      qd.p = p;
+      qd.e = 0;
+      EC_CREATE(&k->u.e);
+      if (!ec_ptparse(&qd, &k->u.e))
+       return (-1);
+      p = qd.p;
+    } break;
+
     /* --- Structured information encoding --- *
      *
      * The format for structured key data is `[NAME=KEY,...]', where the
@@ -183,7 +219,7 @@ int key_read(const char *p, key_data *k, char **pp)
 
        {
          unsigned f;
-         ks = sym_find(&k->u.s, d.buf, d.len + 1, sizeof(*ks), &f);
+         ks = sym_find(&k->u.s, d.buf, d.len, sizeof(*ks), &f);
          if (f)
            key_destroy(&ks->k);
        }
@@ -272,6 +308,24 @@ int key_write(key_data *k, dstr *d, const key_filter *kf)
       mp_writedstr(k->u.m, d, 10);
       rc = 1;
       break;
+    case KENC_STRING: {
+      const char *p = k->u.p;
+      key_writeflags(k->e, d);
+      DPUTC(d, ':');
+      while (*p) {
+       if (*p == ' ') DPUTC(d, '+');
+       else if (!isalnum((unsigned char)*p)) dstr_putf(d, "%%%02x", *p);
+       else DPUTC(d, *p);
+       p++;
+      }
+      rc = 1;
+    } break;
+    case KENC_EC:
+      key_writeflags(k->e, d);
+      DPUTS(d, ":0x"); mp_writedstr(k->u.e.x, d, 16);
+      DPUTS(d, ",0x"); mp_writedstr(k->u.e.y, d, 16);
+      rc = 1;
+      break;
     case KENC_STRUCT: {
       sym_iter i;
       key_struct *ks;