source: libabac/abac_pl_yap.c @ e95d652

mei_rt2mei_rt2_fix_1meiyap-rt1meiyap1rt2
Last change on this file since e95d652 was e95d652, checked in by Mei <mei@…>, 13 years ago

1) added yap, flex, bison to bring in prolog backend

  • Property mode set to 100644
File size: 7.3 KB
Line 
1
2/* copied from abac_graph.c
3   implementation of the low level using
4   yap prolog
5*/
6
7#include <err.h>
8#include <stdio.h>
9#include <assert.h>
10#include <stdlib.h>
11#include <string.h>
12#include <Yap/YapInterface.h>
13
14#include "abac_pl.h"
15#include "abac_pl_yap.h"
16
17#include "abac_list.h"
18#include "abac_util.h"
19
20#include "uthash.h"
21
22static int _insert_clause(char*);
23static void _show_yap_db(char*);
24
25extern char *abac_cn_with_role(abac_role_t *);
26
27// pl
28struct _abac_pl_t {
29    FILE *fptr;
30    char *fname;
31    char *yap_certs;
32};
33
34/**
35 * Create a new yap structure.
36 */
37abac_pl_t *abac_pl_new(void) {
38
39    if (YAP_FastInit(NULL) == YAP_BOOT_ERROR)
40        YAP_Exit(1);
41
42    if (YAP_RunGoal(YAP_MkAtomTerm(YAP_LookupAtom("source")))) {
43        printf("calling source..\n");
44        } else {
45        printf("calling source failed..\n");
46        YAP_Exit(1);
47    }
48    abac_pl_t *pl = abac_xmalloc(sizeof(abac_pl_t));
49    pl->fptr=NULL;
50    pl->fname=NULL;
51    pl->yap_certs=NULL;
52    return pl;
53}
54
55/**
56 * Add a credential to the credential pl.
57 */
58int abac_pl_add_credential(abac_pl_t *pl, abac_credential_t *cred)
59{
60    int rc=0;
61    char *str = abac_credential_clause(cred);
62    if (str != NULL) {
63        rc=_insert_clause(str);
64    }
65    _show_yap_db("calling within abac_pl_add_credential");
66    return rc;
67}
68
69static int _insert_clause(char *cstr)
70{
71    int ret=ABAC_CERT_SUCCESS;
72    YAP_Term *eterm;
73    YAP_Term goalArgs=YAP_ReadBuffer(cstr, eterm);
74    char *tmp=YAP_CompileClause(goalArgs);
75    if (tmp!=NULL) { /* something is wrong */
76        printf("error: result of compile clause (%s)\n", tmp);
77        ret=ABAC_CERT_BAD_YAP;
78    }
79    return ret;
80}
81
82static void _show_yap_db(char *msg)
83{
84    char lstr[]="listing";
85    YAP_Term *eterm;
86
87    YAP_Term goal=YAP_ReadBuffer(lstr, eterm);
88    printf("calling listing..from(%s) \n",msg);
89    int rc =YAP_RunGoal( goal );
90    if (rc) {
91        printf("listing ok.. \n");
92    } else {
93        printf("listing's rc is bad.. \n");
94        YAP_Exit(1);
95    }
96}
97
98static void _set_dbg(abac_pl_t *pl)
99{
100    char *fname=strdup( "/tmp/abac_yap-XXXXXX.pl" );
101    int fd = mkstemps( pl->fname, 3 );
102    if ( fd == -1) {
103        printf("Couldn't get a valid temp name %s\n", fname);
104        free((void*)fname);
105        YAP_Exit(1);
106    }
107    FILE *fptr = fdopen(fd, "w");
108    if (fptr == NULL) {
109        printf("Couldn't open %s for writing\n", fname);
110        free((void*)fname);
111        YAP_Exit(1);
112    }
113    pl->fptr=fptr;
114    pl->fname=fname;
115}
116
117static abac_list_t *_linked_query(abac_pl_t *pl, abac_role_t* role, abac_role_t* role_prin )
118{
119    abac_list_t *cred_list = abac_list_new();
120    return cred_list;
121}
122
123static abac_list_t *_intersect_query(abac_pl_t *pl, abac_role_t* role, abac_role_t* role_prin )
124{
125    abac_list_t *cred_list = abac_list_new();
126    return cred_list;
127}
128
129
130/* cases,
131     ['str']
132     ['str1','str2']
133     ([] is not possible, and don't care)
134*/
135static void _credentials_from_string(abac_list_t *credentials,char *slist) {
136    char *cptr=slist; /* current ptr */
137    char *sptr; /* string ptr */
138    char *ptr;
139    int len=strlen(ptr);
140    char *string;
141    abac_credential_t *cred=NULL;
142
143    /* find first [' */ 
144    ptr=strstr(cptr,"['");
145    if(ptr == NULL) 
146         return;
147    cptr=ptr+2;
148    sptr=cptr;
149    while (1) {
150        /* find next ',' or '] */
151        ptr=strstr(cptr,"','");
152        if(ptr!=NULL) {
153             cptr=ptr+3;
154             len=ptr-sptr;
155             string=strndup(sptr,len);
156             printf("string found(%s)\n", string); 
157             cred=abac_credential_lookup(string);
158             if(cred) {
159                 abac_list_add(credentials, abac_credential_dup(cred));
160                 } else {
161                 printf("BAD BAD BAD\n");
162             }
163             sptr=cptr;
164             } else {
165             ptr=strstr(cptr,"']");
166             if(ptr!=NULL) {
167                 len=ptr-sptr;
168                 string=strndup(sptr,len);
169                 printf("last string found(%s)\n", string); 
170                 cred=abac_credential_lookup(string);
171                 if(cred) {
172                     abac_list_add(credentials, abac_credential_dup(cred));
173                     } else {
174                     printf("BAD BAD BAD\n");
175                 }
176                 break;
177             }
178        }
179    }
180}
181
182/* 2 types
183      acme.buys_rocket <- coyote
184      acme.buys_rocket <- acme.preferred_customer  -- NOT DONE YET */
185static abac_list_t *_query(abac_pl_t *pl, abac_role_t* role, abac_role_t* role_prin )
186{
187    YAP_Term *eterm;
188    YAP_Term arg[3];
189    char tmp[1000];
190    abac_list_t *cred_list = NULL;
191
192    char *cn_prin=abac_cn_with_role(role_prin);
193    char *cn_role=abac_cn_with_role(role);
194
195    if(abac_role_role_name(role_prin)!=NULL) {
196        printf("NOT YET DONE, role_prin is B.R !!!\n");
197        YAP_Exit(1);
198    }
199
200    if (cn_prin == NULL || cn_role == NULL) {
201        printf("fail, query's call got bad roles.. \n");
202        YAP_Exit(1);
203    }
204    sprintf(tmp,"role(%s,%s)", cn_role, abac_role_role_name(role));
205    arg[0]=YAP_MkAtomTerm(YAP_LookupAtom(cn_prin));
206    arg[1]=YAP_ReadBuffer(tmp,eterm);
207    arg[2]=YAP_MkVarTerm();
208    YAP_Atom f = YAP_LookupAtom("isMember");
209    YAP_Functor func = YAP_MkFunctor(f, 3);
210    YAP_Term goal=YAP_MkApplTerm(func, 3, arg);
211    int rc =YAP_RunGoal( goal );
212    if (rc) {
213        cred_list = abac_list_new();
214        printf("success, query call ok.. \n");
215        YAP_WriteBuffer(arg[2], tmp, 1000,YAP_WRITE_HANDLE_VARS);
216        printf("    answer : %s(%d)\n", tmp, strlen(tmp));
217        /* this is returned as ['string1','string2'] */
218        _credentials_from_string(cred_list,tmp); 
219        while (YAP_RestartGoal()) {
220            printf("another success\n");
221            YAP_WriteBuffer(arg[2], tmp, 1000,YAP_WRITE_HANDLE_VARS);
222            printf("    answer : %s\n", tmp);
223            _credentials_from_string(cred_list,tmp); 
224        }
225    } else {
226        printf("fail, query's call is bad.. \n");
227        YAP_Exit(1);
228    }
229    return cred_list;
230}
231
232/**
233 * Make a query into prolog db
234--role acme.preferred_customer --principal coyote
235--role acme.prefer_customer.buy_rockets --principlal coyote
236 */
237abac_list_t *abac_pl_query(abac_pl_t *pl, char *role_name, char *principal)
238{
239    abac_role_t *role = abac_role_from_string(role_name);
240    abac_role_t *prin_role = abac_role_from_string(principal);
241    char *query_clause = NULL;
242    abac_list_t *ret=NULL;
243
244    // give up on bogus roles
245    if (role == NULL || prin_role == NULL) {
246        free(role);
247        free(prin_role);
248        return NULL;
249    }
250
251    /* should be using yacc */
252/* if role->prereqs != NULL (&) */
253    if (abac_role_is_intersection(role)) {
254/* XXX */
255        ret=_intersect_query(pl,role,prin_role);
256    /* prin.role.role1 */
257    } else if( abac_role_linked_role(role) ) {
258/* XXX */
259        ret=_linked_query(pl,role,prin_role);
260    } else {  /* prin.role,  */
261        ret=_query(pl,role,prin_role);
262    }
263
264    return ret;
265}
266
267/**
268 * Get all the credentials (attribute/issuer cert pairs) from prolog
269 * (which returns in string form)
270 */
271abac_list_t *abac_pl_credentials(abac_pl_t *pl) {
272    abac_list_t *credentials = abac_list_new();
273    /* fix up a stream to stream the credentials from prolog engine */
274    return credentials;
275}
276
277void abac_pl_free(abac_pl_t *pl) {
278    if(pl->fptr) {
279        fflush(pl->fptr);
280        free(pl->fptr);
281    }
282    if(pl->fname) {
283        unlink(pl->fname);
284        free(pl->fname);
285    }
286    free(pl);
287}
288
Note: See TracBrowser for help on using the repository browser.