Annotation of parser3/src/types/pa_value.C, revision 1.9.2.6
1.1 paf 1: /** @file
2: Parser: Value class.
3:
1.9 paf 4: Copyright (c) 2001, 2003 ArtLebedev Group (http://www.artlebedev.com)
1.1 paf 5: Author: Alexandr Petrosian <paf@design.ru> (http://paf.design.ru)
1.2 paf 6: */
1.1 paf 7:
1.9.2.6 ! paf 8: static const char* IDENT_VALUE_C="$Date: 2003/01/30 09:14:01 $";
1.1 paf 9:
10: #include "pa_value.h"
1.9.2.5 paf 11: #include "pa_value_includes.h"
1.1 paf 12: #include "pa_vstateless_class.h"
1.4 paf 13: #include "pa_vmethod_frame.h"
1.9.2.5 paf 14: #include "pa_vdate.h"
1.9.2.3 paf 15:
16: // globals
17:
18: StringPtr value_name(new String(VALUE_NAME));
1.9.2.4 paf 19: StringPtr content_type_name(new String(CONTENT_TYPE_NAME));
1.9.2.3 paf 20:
21: // methods
1.9.2.2 paf 22:
1.9.2.5 paf 23: VFilePtr Value::as_vfile(Pool& /*pool*/, String::Untaint_lang /*lang*/, bool /*origins_mode*/) {
1.9.2.2 paf 24: bark("(%s) does not have file value");
1.9.2.5 paf 25: return 0; //never
1.9.2.2 paf 26: }
1.1 paf 27:
28: /// call this before invoking to ensure proper actual numbered params count
29: void Method::check_actual_numbered_params(
1.9.2.6 ! paf 30: Value& self, StringPtr actual_name, MethodParams& actual_numbered_params) const {
1.1 paf 31:
1.9.2.5 paf 32: int actual_count=actual_numbered_params.count();
1.1 paf 33: if(actual_count<min_numbered_params_count) // not proper count? bark
34: throw Exception("parser.runtime",
1.9.2.5 paf 35: actual_name,
1.1 paf 36: "native method of %s (%s) accepts minimum %d parameter(s) (%d present)",
1.8 paf 37: self.get_class()->name_cstr(),
38: self.type(),
1.1 paf 39: min_numbered_params_count,
40: actual_count);
41:
42: }
1.4 paf 43:
1.9.2.5 paf 44: Junction::Junction(Value& aself,
45: const Method* amethod,
46: VMethodFrame* amethod_frame,
47: Value* arcontext,
48: WContext* awcontext,
49: ArrayOperationPtr acode): self(aself),
1.7 paf 50: method(amethod),
1.4 paf 51: method_frame(amethod_frame),
52: rcontext(arcontext),
53: wcontext(awcontext),
54: code(acode) {
1.5 paf 55: if(wcontext)
1.9.2.5 paf 56: wcontext->attach_junction(JunctionPtr(this));
1.4 paf 57: }
58:
1.5 paf 59: void Junction::reattach(WContext *new_wcontext) {
60: if(new_wcontext)
61: wcontext=new_wcontext;
62: else {
63: method_frame=0;
64: rcontext=0;
65: wcontext=0;
66: }
1.4 paf 67: }
68:
69: /*
70: void Junction::change_context(Junction *source) {
71: if(source) {
72: method_frame=source->method_frame;
73: rcontext=source->rcontext;
74: wcontext=source->wcontext;
75: } else {
76: method_frame=rcontext=0;
77: wcontext=0;
78: }
79: }
80: */
81:
1.9.2.1 paf 82: // attributed meaning
83:
84: static size_t date_attribute(const VDate& vdate, char *buf, size_t buf_size) {
85: const char month_names[12][4]={
86: "Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"};
87: const char days[7][4]={
88: "Sun","Mon","Tue","Wed","Thu","Fri","Sat"};
89:
90: time_t when=vdate.get_time();
91: struct tm *tms=gmtime(&when);
92: if(!tms)
1.9.2.5 paf 93: throw Exception(Exception::undefined_type,
94: Exception::undefined_source,
1.9.2.1 paf 95: "bad time in attribute value (seconds from epoch=%ld)", when);
96: return snprintf(buf, MAX_STRING, "%s, %.2d-%s-%.4d %.2d:%.2d:%.2d GMT",
97: days[tms->tm_wday],
98: tms->tm_mday,month_names[tms->tm_mon],tms->tm_year+1900,
99: tms->tm_hour,tms->tm_min,tms->tm_sec);
100: }
1.9.2.5 paf 101: static void append_attribute_meaning(Pool& pool,
102: String* result,
103: ValuePtr value, String::Untaint_lang lang, bool forced) {
1.9.2.6 ! paf 104: if(StringPtr string=value->get_string(&pool))
1.9.2.5 paf 105: result->append(*string->join_chains(pool), lang, forced);
1.9.2.1 paf 106: else
1.9.2.5 paf 107: if(ValuePtr vdate=value->as(VDATE_TYPE, false)) {
108: char *buf=new(pool) char[MAX_STRING];
109: size_t size=date_attribute(static_cast<VDate&>(*vdate),
1.9.2.1 paf 110: buf, MAX_STRING);
111:
1.9.2.5 paf 112: result->APPEND_CLEAN(buf, size, "converted from date", 0);
1.9.2.1 paf 113: } else
114: throw Exception("parser.runtime",
1.9.2.6 ! paf 115: StringPtr(result),
1.9.2.1 paf 116: "trying to append here neither string nor date (%s)",
1.9.2.5 paf 117: value->type());
1.9.2.1 paf 118: }
119: #ifndef DOXYGEN
120: struct Attributed_meaning_info {
1.9.2.5 paf 121: Pool* pool;
122: String* header; // header line being constructed
1.9.2.1 paf 123: String::Untaint_lang lang; // language in which to append to that line
124: bool forced; // do they force that lang?
125: };
126: #endif
1.9.2.5 paf 127: static void append_attribute_subattribute(
128: HashStringValue::key_type akey,
129: HashStringValue::value_type avalue,
130: Attributed_meaning_info *info) {
131: if(*akey==VALUE_NAME)
1.9.2.1 paf 132: return;
133:
134: // ...; charset=windows1251
1.9.2.5 paf 135: *info->header << "; ";
136: info->header->append(*akey, info->lang, info->forced);
137: *info->header << "=";
138: append_attribute_meaning(*info->pool, info->header, avalue, info->lang, info->forced);
1.9.2.1 paf 139: }
1.9.2.6 ! paf 140: StringPtr attributed_meaning_to_string(Pool& pool,
1.9.2.5 paf 141: ValuePtr meaning,
1.9.2.1 paf 142: String::Untaint_lang lang, bool forced) {
1.9.2.5 paf 143: StringPtr result(new String);
1.9.2.6 ! paf 144: if(HashStringValue *hash=meaning->get_hash(StringPtr(0))) {
1.9.2.1 paf 145: // $value(value) $subattribute(subattribute value)
1.9.2.5 paf 146: if(ValuePtr value=hash->get(value_name))
147: append_attribute_meaning(pool, &*result, value, lang, forced);
1.9.2.1 paf 148:
1.9.2.5 paf 149: Attributed_meaning_info attributed_meaning_info={&pool, &*result, lang};
1.9.2.1 paf 150: hash->for_each(append_attribute_subattribute, &attributed_meaning_info);
151: } else // result value
1.9.2.5 paf 152: append_attribute_meaning(pool, &*result, meaning, lang, forced);
1.9.2.1 paf 153:
154: return result;
155: }
E-mail: