summaryrefslogtreecommitdiff
path: root/sys/src/libauth/attr.c
diff options
context:
space:
mode:
authorTaru Karttunen <taruti@taruti.net>2011-03-30 15:46:40 +0300
committerTaru Karttunen <taruti@taruti.net>2011-03-30 15:46:40 +0300
commite5888a1ffdae813d7575f5fb02275c6bb07e5199 (patch)
treed8d51eac403f07814b9e936eed0c9a79195e2450 /sys/src/libauth/attr.c
Import sources from 2011-03-30 iso image
Diffstat (limited to 'sys/src/libauth/attr.c')
-rwxr-xr-xsys/src/libauth/attr.c174
1 files changed, 174 insertions, 0 deletions
diff --git a/sys/src/libauth/attr.c b/sys/src/libauth/attr.c
new file mode 100755
index 000000000..5f35750ba
--- /dev/null
+++ b/sys/src/libauth/attr.c
@@ -0,0 +1,174 @@
+#include <u.h>
+#include <libc.h>
+#include <auth.h>
+
+int
+_attrfmt(Fmt *fmt)
+{
+ char *b, buf[1024], *ebuf;
+ Attr *a;
+
+ ebuf = buf+sizeof buf;
+ b = buf;
+ strcpy(buf, " ");
+ for(a=va_arg(fmt->args, Attr*); a; a=a->next){
+ if(a->name == nil)
+ continue;
+ switch(a->type){
+ case AttrQuery:
+ b = seprint(b, ebuf, " %q?", a->name);
+ break;
+ case AttrNameval:
+ b = seprint(b, ebuf, " %q=%q", a->name, a->val);
+ break;
+ case AttrDefault:
+ b = seprint(b, ebuf, " %q:=%q", a->name, a->val);
+ break;
+ }
+ }
+ return fmtstrcpy(fmt, buf+1);
+}
+
+Attr*
+_copyattr(Attr *a)
+{
+ Attr **la, *na;
+
+ na = nil;
+ la = &na;
+ for(; a; a=a->next){
+ *la = _mkattr(a->type, a->name, a->val, nil);
+ setmalloctag(*la, getcallerpc(&a));
+ la = &(*la)->next;
+ }
+ *la = nil;
+ return na;
+}
+
+Attr*
+_delattr(Attr *a, char *name)
+{
+ Attr *fa;
+ Attr **la;
+
+ for(la=&a; *la; ){
+ if(strcmp((*la)->name, name) == 0){
+ fa = *la;
+ *la = (*la)->next;
+ fa->next = nil;
+ _freeattr(fa);
+ }else
+ la=&(*la)->next;
+ }
+ return a;
+}
+
+Attr*
+_findattr(Attr *a, char *n)
+{
+ for(; a; a=a->next)
+ if(strcmp(a->name, n) == 0 && a->type != AttrQuery)
+ return a;
+ return nil;
+}
+
+void
+_freeattr(Attr *a)
+{
+ Attr *anext;
+
+ for(; a; a=anext){
+ anext = a->next;
+ free(a->name);
+ free(a->val);
+ a->name = (void*)~0;
+ a->val = (void*)~0;
+ a->next = (void*)~0;
+ free(a);
+ }
+}
+
+Attr*
+_mkattr(int type, char *name, char *val, Attr *next)
+{
+ Attr *a;
+
+ a = malloc(sizeof(*a));
+ if(a==nil)
+ sysfatal("_mkattr malloc: %r");
+ a->type = type;
+ a->name = strdup(name);
+ a->val = strdup(val);
+ if(a->name==nil || a->val==nil)
+ sysfatal("_mkattr malloc: %r");
+ a->next = next;
+ setmalloctag(a, getcallerpc(&type));
+ return a;
+}
+
+static Attr*
+cleanattr(Attr *a)
+{
+ Attr *fa;
+ Attr **la;
+
+ for(la=&a; *la; ){
+ if((*la)->type==AttrQuery && _findattr(a, (*la)->name)){
+ fa = *la;
+ *la = (*la)->next;
+ fa->next = nil;
+ _freeattr(fa);
+ }else
+ la=&(*la)->next;
+ }
+ return a;
+}
+
+Attr*
+_parseattr(char *s)
+{
+ char *p, *t, *tok[256];
+ int i, ntok, type;
+ Attr *a;
+
+ s = strdup(s);
+ if(s == nil)
+ sysfatal("_parseattr strdup: %r");
+
+ ntok = tokenize(s, tok, nelem(tok));
+ a = nil;
+ for(i=ntok-1; i>=0; i--){
+ t = tok[i];
+ if(p = strchr(t, '=')){
+ *p++ = '\0';
+ // if(p-2 >= t && p[-2] == ':'){
+ // p[-2] = '\0';
+ // type = AttrDefault;
+ // }else
+ type = AttrNameval;
+ a = _mkattr(type, t, p, a);
+ setmalloctag(a, getcallerpc(&s));
+ }
+ else if(t[strlen(t)-1] == '?'){
+ t[strlen(t)-1] = '\0';
+ a = _mkattr(AttrQuery, t, "", a);
+ setmalloctag(a, getcallerpc(&s));
+ }else{
+ /* really a syntax error, but better to provide some indication */
+ a = _mkattr(AttrNameval, t, "", a);
+ setmalloctag(a, getcallerpc(&s));
+ }
+ }
+ free(s);
+ return cleanattr(a);
+}
+
+char*
+_strfindattr(Attr *a, char *n)
+{
+ a = _findattr(a, n);
+ if(a == nil)
+ return nil;
+ return a->val;
+}
+