rpki-client: some signed object boiler plate

Theo Buehler <[email protected]>
Newsgroups gmane.os.openbsd.tech
Message-ID <[email protected]>
This diff adds new/free/obj functions and introduces struct signed_obj
containing the handlers. For now I pass der_len and time_t into the
new function, this isn't particularly safe since the compiler won't
complain if we call sobj->new(signtime, der_len) in the future. We can
switch to a different approach in a later step.

For now only _new() is used in the _parse() functions. More wiring
up will happen in a later step.

Index: aspa.c
===================================================================
RCS file: /cvs/src/usr.sbin/rpki-client/aspa.c,v
diff -u -p -r1.43 aspa.c
--- aspa.c	17 Jun 2026 08:22:21 -0000	1.43
+++ aspa.c	22 Jun 2026 12:47:49 -0000
@@ -179,6 +179,39 @@ aspa_validate(const char *fn, void *obj,
 	return 1; /* XXX */
 }
 
+static void *
+aspa_obj_new(size_t der_len, time_t signtime)
+{
+	struct aspa *aspa;
+
+	if ((aspa = calloc(1, sizeof(*aspa))) == NULL)
+		err(1, NULL);
+	aspa->signtime = signtime;
+
+	return aspa;
+}
+
+static void
+aspa_obj_free(void *obj)
+{
+	aspa_free(obj);
+}
+
+static const struct signed_obj aspa_signed_obj = {
+	.rtype = RTYPE_ASPA,
+	.new = aspa_obj_new,
+	.free = aspa_obj_free,
+	.cert_info = aspa_cert_info,
+	.parse_econtent = aspa_parse_econtent,
+	.validate = aspa_validate,
+};
+
+const struct signed_obj *
+aspa_obj(void)
+{
+	return &aspa_signed_obj;
+}
+
 /*
  * Parse a full ASPA file.
  * Returns the payload or NULL if the file was malformed.
@@ -201,10 +234,7 @@ aspa_parse(struct cert **out_cert, const
 	if (cms == NULL)
 		return NULL;
 
-	if ((aspa = calloc(1, sizeof(*aspa))) == NULL)
-		err(1, NULL);
-	aspa->signtime = signtime;
-
+	aspa = aspa_obj_new(len, signtime);
 	if (!aspa_cert_info(fn, aspa, cert))
 		goto out;
 	if (!aspa_parse_econtent(fn, aspa, cms, cmsz))
Index: extern.h
===================================================================
RCS file: /cvs/src/usr.sbin/rpki-client/extern.h,v
diff -u -p -r1.283 extern.h
--- extern.h	22 Jun 2026 08:08:03 -0000	1.283
+++ extern.h	22 Jun 2026 12:47:49 -0000
@@ -212,6 +212,17 @@ enum location {
 	DIR_VALID,
 };
 
+struct signed_obj {
+	enum rtype rtype;
+	void *(*new)(size_t, time_t);
+	void (*free)(void *);
+	int (*cert_info)(const char *, void *, const struct cert *);
+	int (*parse_econtent)(const char *, void *, const uint8_t *, size_t);
+	int (*parse_detached)(const char *, void *, BIO *, char *, size_t,
+	    uint8_t **, size_t *);
+	int (*validate)(const char *, void *, struct cert *);
+};
+
 /*
  * Files specified in an MFT have their bodies hashed with SHA256.
  */
@@ -732,6 +743,7 @@ void		 mft_buffer(struct ibuf *, const s
 void		 mft_free(struct mft *);
 struct mft	*mft_parse(struct cert **, const char *, int,
 		    const unsigned char *, size_t);
+const struct signed_obj *mft_obj(void);
 struct mft	*mft_read(struct ibuf *);
 int		 mft_compare_issued(const struct mft *, const struct mft *);
 int		 mft_compare_seqnum(const struct mft *, const struct mft *);
@@ -742,6 +754,7 @@ void		 roa_buffer(struct ibuf *, const s
 void		 roa_free(struct roa *);
 struct roa	*roa_parse(struct cert **, const char *, int,
 		    const unsigned char *, size_t);
+const struct signed_obj *roa_obj(void);
 struct roa	*roa_read(struct ibuf *);
 void		 roa_insert_vrps(struct vrp_tree *, struct roa *,
 		    struct repo *);
@@ -750,6 +763,7 @@ void		 spl_buffer(struct ibuf *, const s
 void		 spl_free(struct spl *);
 struct spl	*spl_parse(struct cert **, const char *, int,
 		    const unsigned char *, size_t);
+const struct signed_obj *spl_obj(void);
 struct spl	*spl_read(struct ibuf *);
 void		 spl_insert_vsps(struct vsp_tree *, struct spl *,
 		    struct repo *);
@@ -757,11 +771,13 @@ void		 spl_insert_vsps(struct vsp_tree *
 void		 rsc_free(struct rsc *);
 struct rsc	*rsc_parse(struct cert **, const char *, int,
 		    const unsigned char *, size_t);
+const struct signed_obj *rsc_obj(void);
 
 void		 takey_free(struct takey *);
 void		 tak_free(struct tak *);
 struct tak	*tak_parse(struct cert **, const char *, int,
 		    const unsigned char *, size_t);
+const struct signed_obj *tak_obj(void);
 
 void		 aspa_buffer(struct ibuf *, const struct aspa *);
 void		 aspa_free(struct aspa *);
@@ -769,6 +785,7 @@ void		 aspa_insert_vaps(char *, struct v
 		    struct repo *);
 struct aspa	*aspa_parse(struct cert **, const char *, int,
 		    const unsigned char *, size_t);
+const struct signed_obj *aspa_obj(void);
 struct aspa	*aspa_read(struct ibuf *);
 
 /* crl.c */
Index: mft.c
===================================================================
RCS file: /cvs/src/usr.sbin/rpki-client/mft.c,v
diff -u -p -r1.140 mft.c
--- mft.c	17 Jun 2026 08:47:28 -0000	1.140
+++ mft.c	22 Jun 2026 12:47:49 -0000
@@ -424,6 +424,40 @@ mft_validate(const char *fn, void *obj, 
 	return 1;
 }
 
+static void *
+mft_obj_new(size_t der_len, time_t signtime)
+{
+	struct mft *mft;
+
+	if ((mft = calloc(1, sizeof(*mft))) == NULL)
+		err(1, NULL);
+	mft->mftsize = der_len;
+	mft->signtime = signtime;
+
+	return mft;
+}
+
+static void
+mft_obj_free(void *obj)
+{
+	mft_free(obj);
+}
+
+static const struct signed_obj mft_signed_obj = {
+	.rtype = RTYPE_MFT,
+	.new = mft_obj_new,
+	.free = mft_obj_free,
+	.cert_info = mft_cert_info,
+	.parse_econtent = mft_parse_econtent,
+	.validate = mft_validate,
+};
+
+const struct signed_obj *
+mft_obj(void)
+{
+	return &mft_signed_obj;
+}
+
 /*
  * Parse the objects that have been published in the manifest.
  * Return mft if it conforms to RFC 9286, otherwise NULL.
@@ -446,11 +480,7 @@ mft_parse(struct cert **out_cert, const 
 	if (cms == NULL)
 		return NULL;
 
-	if ((mft = calloc(1, sizeof(*mft))) == NULL)
-		err(1, NULL);
-	mft->signtime = signtime;
-	mft->mftsize = len;
-
+	mft = mft_obj_new(len, signtime);
 	if (!mft_cert_info(fn, mft, cert))
 		goto out;
 	if (!mft_parse_econtent(fn, mft, cms, cmsz))
Index: roa.c
===================================================================
RCS file: /cvs/src/usr.sbin/rpki-client/roa.c,v
diff -u -p -r1.89 roa.c
--- roa.c	17 Jun 2026 08:47:28 -0000	1.89
+++ roa.c	22 Jun 2026 12:47:49 -0000
@@ -236,6 +236,39 @@ roa_validate(const char *fn, void *obj, 
 	return 1; /* XXX */
 }
 
+static void *
+roa_obj_new(size_t der_len, time_t signtime)
+{
+	struct roa *roa;
+
+	if ((roa = calloc(1, sizeof(*roa))) == NULL)
+		err(1, NULL);
+	roa->signtime = signtime;
+
+	return roa;
+}
+
+static void
+roa_obj_free(void *obj)
+{
+	roa_free(obj);
+}
+
+static const struct signed_obj roa_signed_obj = {
+	.rtype = RTYPE_ROA,
+	.new = roa_obj_new,
+	.free = roa_obj_free,
+	.cert_info = roa_cert_info,
+	.parse_econtent = roa_parse_econtent,
+	.validate = roa_validate,
+};
+
+const struct signed_obj *
+roa_obj(void)
+{
+	return &roa_signed_obj;
+}
+
 /*
  * Parse a full RFC 9582 file.
  * Returns the ROA or NULL if the document was malformed.
@@ -258,10 +291,7 @@ roa_parse(struct cert **out_cert, const 
 	if (cms == NULL)
 		return NULL;
 
-	if ((roa = calloc(1, sizeof(struct roa))) == NULL)
-		err(1, NULL);
-	roa->signtime = signtime;
-
+	roa = roa_obj_new(len, signtime);
 	if (!roa_cert_info(fn, roa, cert))
 		goto out;
 	if (!roa_parse_econtent(fn, roa, cms, cmsz))
Index: rsc.c
===================================================================
RCS file: /cvs/src/usr.sbin/rpki-client/rsc.c,v
diff -u -p -r1.45 rsc.c
--- rsc.c	17 Jun 2026 08:22:21 -0000	1.45
+++ rsc.c	22 Jun 2026 12:47:49 -0000
@@ -361,6 +361,39 @@ rsc_validate(const char *fn, void *obj, 
 	return 1; /* XXX */
 }
 
+static void *
+rsc_obj_new(size_t der_len, time_t signtime)
+{
+	struct rsc *rsc;
+
+	if ((rsc = calloc(1, sizeof(*rsc))) == NULL)
+		err(1, NULL);
+	rsc->signtime = signtime;
+
+	return rsc;
+}
+
+static void
+rsc_obj_free(void *obj)
+{
+	rsc_free(obj);
+}
+
+static const struct signed_obj rsc_signed_obj = {
+	.rtype = RTYPE_RSC,
+	.new = rsc_obj_new,
+	.free = rsc_obj_free,
+	.cert_info = rsc_cert_info,
+	.parse_econtent = rsc_parse_econtent,
+	.validate = rsc_validate,
+};
+
+const struct signed_obj *
+rsc_obj(void)
+{
+	return &rsc_signed_obj;
+}
+
 /*
  * Parse a full RFC 9323 file.
  * Returns the RSC or NULL if the object was malformed.
@@ -383,10 +416,7 @@ rsc_parse(struct cert **out_cert, const 
 	if (cms == NULL)
 		return NULL;
 
-	if ((rsc = calloc(1, sizeof(struct rsc))) == NULL)
-		err(1, NULL);
-	rsc->signtime = signtime;
-
+	rsc = rsc_obj_new(len, signtime);
 	if (!rsc_cert_info(fn, rsc, cert))
 		goto out;
 	if (!rsc_parse_econtent(fn, rsc, cms, cmsz))
Index: spl.c
===================================================================
RCS file: /cvs/src/usr.sbin/rpki-client/spl.c,v
diff -u -p -r1.17 spl.c
--- spl.c	17 Jun 2026 08:22:21 -0000	1.17
+++ spl.c	22 Jun 2026 12:47:49 -0000
@@ -241,6 +241,39 @@ spl_validate(const char *fn, void *obj, 
 	return 1; /* XXX */
 }
 
+static void *
+spl_obj_new(size_t der_len, time_t signtime)
+{
+	struct spl *spl;
+
+	if ((spl = calloc(1, sizeof(*spl))) == NULL)
+		err(1, NULL);
+	spl->signtime = signtime;
+
+	return spl;
+}
+
+static void
+spl_obj_free(void *obj)
+{
+	spl_free(obj);
+}
+
+static const struct signed_obj spl_signed_obj = {
+	.rtype = RTYPE_SPL,
+	.new = spl_obj_new,
+	.free = spl_obj_free,
+	.cert_info = spl_cert_info,
+	.parse_econtent = spl_parse_econtent,
+	.validate = spl_validate,
+};
+
+const struct signed_obj *
+spl_obj(void)
+{
+	return &spl_signed_obj;
+}
+
 /*
  * Parse a full Signed Prefix List file.
  * Returns the SPL, or NULL if the object was malformed.
@@ -263,10 +296,7 @@ spl_parse(struct cert **out_cert, const 
 	if (cms == NULL)
 		return NULL;
 
-	if ((spl = calloc(1, sizeof(*spl))) == NULL)
-		err(1, NULL);
-	spl->signtime = signtime;
-
+	spl = spl_obj_new(len, signtime);
 	if (!spl_cert_info(fn, spl, cert))
 		goto out;
 	if (!spl_parse_econtent(fn, spl, cms, cmsz))
Index: tak.c
===================================================================
RCS file: /cvs/src/usr.sbin/rpki-client/tak.c,v
diff -u -p -r1.30 tak.c
--- tak.c	17 Jun 2026 08:22:21 -0000	1.30
+++ tak.c	22 Jun 2026 12:47:49 -0000
@@ -208,6 +208,39 @@ tak_validate(const char *fn, void *obj, 
 	return 1;
 }
 
+static void *
+tak_obj_new(size_t der_len, time_t signtime)
+{
+	struct tak *tak;
+
+	if ((tak = calloc(1, sizeof(*tak))) == NULL)
+		err(1, NULL);
+	tak->signtime = signtime;
+
+	return tak;
+}
+
+static void
+tak_obj_free(void *obj)
+{
+	tak_free(obj);
+}
+
+static const struct signed_obj tak_signed_obj = {
+	.rtype = RTYPE_SPL,
+	.new = tak_obj_new,
+	.free = tak_obj_free,
+	.cert_info = tak_cert_info,
+	.parse_econtent = tak_parse_econtent,
+	.validate = tak_validate,
+};
+
+const struct signed_obj *
+tak_obj(void)
+{
+	return &tak_signed_obj;
+}
+
 /*
  * Parse a full RFC 9691 Trust Anchor Key file.
  * Returns the TAK or NULL if the object was malformed.
@@ -230,10 +263,7 @@ tak_parse(struct cert **out_cert, const 
 	if (cms == NULL)
 		return NULL;
 
-	if ((tak = calloc(1, sizeof(struct tak))) == NULL)
-		err(1, NULL);
-	tak->signtime = signtime;
-
+	tak = tak_obj_new(len, signtime);
 	if (!tak_cert_info(fn, tak, cert))
 		goto out;
 	if (!tak_parse_econtent(fn, tak, cms, cmsz))
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.