Commit 779cb492 authored by Luis R. Rodriguez's avatar Luis R. Rodriguez

crda: add regulatory domain stream parser

This adds a stream parser for regulatory domains. This
allows developers to build regulatory domains now using
the db.txt from a stream, either stdin, or a from an
opened file.

This also adds a simple db2rd which for now only uses the
library but with a bit of effort can also be used as a
suitable replacement for the kernel's genregdb.awk.
Signed-off-by: 's avatarLuis R. Rodriguez <>
parent 231a1097
......@@ -24,10 +24,11 @@ PUBKEY_DIR?=pubkeys
CFLAGS += -Wall -g
LDLIBS += -lm
all: all_noverify verify
all_noverify: crda intersect regdbdump
all_noverify: crda intersect regdbdump db2rd
ifeq ($(USE_OPENSSL),1)
CFLAGS += -DUSE_OPENSSL -DPUBKEY_DIR=\"$(RUNTIME_PUBKEY_DIR)\" `pkg-config --cflags openssl`
......@@ -121,6 +122,10 @@ intersect: reglib.o intersect.o
$(NQ) ' LD ' $@
$(Q)$(CC) $(CFLAGS) $(LDFLAGS) -o $@ $^ $(LDLIBS)
db2rd: reglib.o db2rd.o
$(NQ) ' LD ' $@
$(Q)$(CC) $(CFLAGS) $(LDFLAGS) -o $@ $^ $(LDLIBS)
verify: $(REG_BIN) regdbdump
$(NQ) ' CHK $(REG_BIN)'
$(Q)./regdbdump $(REG_BIN) >/dev/null
......@@ -152,5 +157,6 @@ install: crda crda.8.gz regdbdump.8.gz
$(Q)$(INSTALL) -m 644 -t $(DESTDIR)/$(MANDIR)/man8/ regdbdump.8.gz
$(Q)rm -f crda regdbdump intersect *.o *~ *.pyc keys-*.c *.gz \
$(Q)rm -f crda regdbdump intersect db2rd \
*.o *~ *.pyc keys-*.c *.gz \
udev/$(UDEV_LEVEL)regulatory.rules udev/regulatory.rules.parsed
#include <errno.h>
#include <stdlib.h>
#include <stdio.h>
#include <arpa/inet.h> /* ntohl */
#include <string.h>
#include "nl80211.h"
#include "reglib.h"
int main(int argc, char **argv)
struct ieee80211_regdomain *rd = NULL;
FILE *fp;
if (argc != 1) {
fprintf(stderr, "Usage: cat db.txt | %s\n", argv[0]);
return -EINVAL;
fp = reglib_create_parse_stream(stdin);
if (!fp)
return -EINVAL;
reglib_for_each_country_stream(fp, rd) {
return 0;
This diff is collapsed.
#ifndef REG_LIB_H
#define REG_LIB_H
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <stdbool.h>
#include <sys/stat.h>
#include <math.h>
#include "regdb.h"
......@@ -35,6 +37,19 @@ struct ieee80211_regdomain {
struct ieee80211_reg_rule reg_rules[];
/* Remove this once upstream nl80211.h gets this */
#define NL80211_RRF_NO_IR (1<<7)
#define REGLIB_MHZ_TO_KHZ(freq) ((freq) * 1000)
#define REGLIB_KHZ_TO_MHZ(freq) ((freq) / 1000)
#define REGLIB_DBI_TO_MBI(gain) ((gain) * 100)
#define REGLIB_MBI_TO_DBI(gain) ((gain) / 100)
#define REGLIB_DBM_TO_MBM(gain) ((gain) * 100)
#define REGLIB_MBM_TO_DBM(gain) ((gain) / 100)
#define REGLIB_MW_TO_DBM(gain) (10 * log10(gain))
* struct reglib_regdb_ctx - reglib regdb context
......@@ -180,4 +195,33 @@ reglib_intersect_rds(const struct ieee80211_regdomain *rd1,
const struct ieee80211_regdomain *
reglib_intersect_regdb(const struct reglib_regdb_ctx *ctx);
* @reglib_create_parse_stream - provide a clean new stream for processing
* @fp: FILE stream, could be stdin, or a stream from an open file.
* In order to parse a stream we recommend to create a new stream
* using this helper. A new stream is preferred in order to work
* with stdin, as otherwise we cannot rewind() and move around
* the stream. This helper will create new stream using tmpfile()
* and also remove all comments. It will be closed and the file
* deleted when the process terminates.
FILE *reglib_create_parse_stream(FILE *fp);
* @reglib_parse_country - parse stream to build a regulatory domain
* @fp: FILE stream, could be stdin, or a stream from an open file.
* Parse stream and return back a built regulatory domain. Returns
* NULL if one could not be built.
struct ieee80211_regdomain *reglib_parse_country(FILE *fp);
#define reglib_for_each_country_stream(__fp, __rd) \
for (__rd = reglib_parse_country(__fp); \
__rd != NULL; \
__rd = reglib_parse_country(__fp)) \
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment