Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: downloads/boost_1_33_1/tools/build/jam_src/class.c @ 12

Last change on this file since 12 was 12, checked in by landauf, 17 years ago

added boost

File size: 3.4 KB
Line 
1/* Copyright Vladiir Prus 2003. Distributed under the Boost */
2/* Software License, Version 1.0. (See accompanying */
3/* file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) */
4
5#include "class.h"
6#include "strings.h"
7#include "variable.h"
8#include "frames.h"
9#include "rules.h"
10#include "newstr.h"
11
12#include "hash.h"
13
14static struct hash* classes = 0;
15
16static void check_defined(LIST* class_names)
17{
18    for (; class_names; class_names = class_names->next) {
19        char** p = &class_names->string;
20        if (!hashcheck(classes, (HASHDATA**)&p)) {
21            printf("Class %s is not defined\n", class_names->string);
22            abort();
23        }
24    }
25}
26
27static char* class_module_name(char* declared_name)
28{
29    string name[1];
30    char* result;
31   
32    string_new(name);
33    string_append(name, "class@");
34    string_append(name, declared_name);
35
36    result = newstr(name->value);
37    string_free(name);
38   
39    return result;
40}
41
42struct import_base_data {
43    char* base_name;
44    module_t* base_module;
45    module_t* class_module;
46};
47
48static void import_base_rule(void* r_, void* d_)
49{
50    RULE* r = (RULE*)r_;
51    RULE* ir1;
52    RULE* ir2;
53    struct import_base_data* d = (struct import_base_data*)d_;
54    string qualified_name[1];
55    int basename_lenght = strlen(d->base_name)+1;
56
57    string_new(qualified_name);
58    string_append(qualified_name, d->base_name);
59    string_push_back(qualified_name, '.');
60    string_append(qualified_name, r->name);   
61
62    ir1 = import_rule(r, d->class_module, r->name);
63    ir2 = import_rule(r, d->class_module, qualified_name->value);
64
65    /* Copy 'exported' flag. */
66    ir1->exported = ir2->exported = r->exported;
67
68    /* If we're importing class method, localize it. */
69    if (r->module == d->base_module
70        || r->module->class_module && r->module->class_module == d->base_module) {
71        ir1->module = ir2->module = d->class_module;       
72    }
73       
74    string_free(qualified_name);
75}
76
77/** For each exported rule 'n', declared in class module for base,
78    imports that rule in 'class' as 'n' and as 'base.n'. Imported
79    rules are localized and marked as exported.
80*/
81static void import_base_rules(module_t* class, char* base)
82{
83    module_t* base_module = bindmodule(class_module_name(base));
84    struct import_base_data d;
85    d.base_name = base;
86    d.base_module = base_module;
87    d.class_module = class;
88
89    if (base_module->rules)
90        hashenumerate(base_module->rules, import_base_rule, &d);
91
92    import_module( imported_modules(base_module), class );
93}
94
95char* make_class_module(LIST* xname, LIST* bases, FRAME* frame)
96{
97    char* name = class_module_name(xname->string);
98    char** pp = &xname->string;
99    module_t* class_module = 0;
100    module_t* outer_module = frame->module;   
101
102    if (!classes)
103        classes = hashinit(sizeof(char*), "classes");
104
105   
106    if (hashcheck(classes, (HASHDATA**)&pp)) {       
107        printf("Class %s already defined\n", xname->string);
108        abort();
109    } else {
110        hashenter(classes, (HASHDATA**)&pp);
111    }
112    check_defined(bases);
113   
114    class_module = bindmodule(name);
115
116    exit_module( outer_module );
117    enter_module( class_module );
118
119    var_set("__name__", xname, VAR_SET);
120    var_set("__bases__", bases, VAR_SET);
121   
122    exit_module( class_module );
123    enter_module( outer_module );
124   
125    for(; bases; bases = bases->next)
126        import_base_rules(class_module, bases->string);
127
128
129
130    return name;
131}
Note: See TracBrowser for help on using the repository browser.