libdap Updated for version 3.18.1
BaseType.cc
1
2// -*- mode: c++; c-basic-offset:4 -*-
3
4// This file is part of libdap, A C++ implementation of the OPeNDAP Data
5// Access Protocol.
6
7// Copyright (c) 2002,2003 OPeNDAP, Inc.
8// Author: James Gallagher <jgallagher@opendap.org>
9//
10// This library is free software; you can redistribute it and/or
11// modify it under the terms of the GNU Lesser General Public
12// License as published by the Free Software Foundation; either
13// version 2.1 of the License, or (at your option) any later version.
14//
15// This library is distributed in the hope that it will be useful,
16// but WITHOUT ANY WARRANTY; without even the implied warranty of
17// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18// Lesser General Public License for more details.
19//
20// You should have received a copy of the GNU Lesser General Public
21// License along with this library; if not, write to the Free Software
22// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
23//
24// You can contact OPeNDAP, Inc. at PO Box 112, Saunderstown, RI. 02874-0112.
25
26// (c) COPYRIGHT URI/MIT 1994-1999
27// Please read the full copyright statement in the file COPYRIGHT_URI.
28//
29// Authors:
30// jhrg,jimg James Gallagher <jgallagher@gso.uri.edu>
31
32// Implementation for BaseType.
33//
34// jhrg 9/6/94
35
36#include "config.h"
37
38#include <cstdio> // for stdin and stdout
39
40#include <sstream>
41#include <string>
42
43//#define DODS_DEBUG
44
45#include "BaseType.h"
46#include "Byte.h"
47#include "Int16.h"
48#include "UInt16.h"
49#include "Int32.h"
50#include "UInt32.h"
51#include "Float32.h"
52#include "Float64.h"
53#include "Str.h"
54#include "Url.h"
55#include "Array.h"
56#include "Structure.h"
57#include "Sequence.h"
58#include "Grid.h"
59
60#include "D4Attributes.h"
61#include "DMR.h"
62#include "XMLWriter.h"
63#include "D4BaseTypeFactory.h"
64
65#include "InternalErr.h"
66
67#include "util.h"
68#include "escaping.h"
69
70#include "debug.h"
71
72using namespace std;
73
74namespace libdap {
75
76// Protected copy mfunc
77
84void
86{
87 DBG(cerr << "In BaseType::m_duplicate for " << bt.name() << endl);
88
89 d_name = bt.d_name;
90 d_type = bt.d_type;
91 d_dataset = bt.d_dataset;
92 d_is_read = bt.d_is_read; // added, reza
93 d_is_send = bt.d_is_send; // added, reza
94 d_in_selection = bt.d_in_selection;
95 d_is_synthesized = bt.d_is_synthesized; // 5/11/2001 jhrg
96
97 d_parent = bt.d_parent; // copy pointers 6/4/2001 jhrg
98
99 d_attr = bt.d_attr; // Deep copy.
100
101 if (bt.d_attributes)
102 d_attributes = new D4Attributes(*bt.d_attributes); // deep copy
103 else
104 d_attributes = 0; // init to null if not used.
105
106 d_is_dap4 = bt.d_is_dap4;
107
108 DBG(cerr << "Exiting BaseType::m_duplicate for " << bt.name() << endl);
109}
110
111// Public mfuncs
112
125BaseType::BaseType(const string &n, const Type &t, bool is_dap4)
126 : d_name(n), d_type(t), d_dataset(""), d_is_read(false), d_is_send(false),
127 d_parent(0), d_attributes(0), d_is_dap4(is_dap4),
128 d_in_selection(false), d_is_synthesized(false)
129{}
130
143BaseType::BaseType(const string &n, const string &d, const Type &t, bool is_dap4)
144 : d_name(n), d_type(t), d_dataset(d), d_is_read(false), d_is_send(false),
145 d_parent(0), d_attributes(0), d_is_dap4(is_dap4),
146 d_in_selection(false), d_is_synthesized(false)
147{}
148
150BaseType::BaseType(const BaseType &copy_from) : DapObj()
151{
152 DBG(cerr << "In BaseTpe::copy_ctor for " << copy_from.name() << endl);
153 m_duplicate(copy_from);
154}
155
156BaseType::~BaseType()
157{
158 DBG2(cerr << "Entering ~BaseType (" << this << ")" << endl);
159
160 if (d_attributes)
161 delete d_attributes;
162
163 DBG2(cerr << "Exiting ~BaseType" << endl);
164}
165
166BaseType &
167BaseType::operator=(const BaseType &rhs)
168{
169 DBG(cerr << "Entering BaseType::operator=" << endl);
170 if (this == &rhs)
171 return *this;
172
173 m_duplicate(rhs);
174
175 DBG(cerr << "Exiting BaseType::operator=" << endl);
176 return *this;
177}
178
184{
185 ostringstream oss;
186 oss << "BaseType (" << this << "):" << endl
187 << " _name: " << name() << endl
188 << " _type: " << type_name() << endl
189 << " _dataset: " << d_dataset << endl
190 << " _read_p: " << d_is_read << endl
191 << " _send_p: " << d_is_send << endl
192 << " _synthesized_p: " << d_is_synthesized << endl
193 << " d_parent: " << d_parent << endl
194 << " d_attr: " << hex << &d_attr << dec << endl;
195
196 return oss.str();
197}
198
214BaseType *
216{
217 BaseType *dest = ptr_duplicate();
218
219 // Copy the D2 attributes from 'this' to dest's D4 Attributes
221
222 dest->set_is_dap4(true);
223
224 return dest;
225}
226
235void
236BaseType::dump(ostream &strm) const
237{
238 strm << DapIndent::LMarg << "BaseType::dump - ("
239 << (void *)this << ")" << endl ;
240 DapIndent::Indent() ;
241
242 strm << DapIndent::LMarg << "name: " << name() << endl ;
243 strm << DapIndent::LMarg << "type: " << type_name() << endl ;
244 strm << DapIndent::LMarg << "dataset: " << d_dataset << endl ;
245 strm << DapIndent::LMarg << "read_p: " << d_is_read << endl ;
246 strm << DapIndent::LMarg << "send_p: " << d_is_send << endl ;
247 strm << DapIndent::LMarg << "synthesized_p: " << d_is_synthesized << endl ;
248 strm << DapIndent::LMarg << "parent: " << (void *)d_parent << endl ;
249 strm << DapIndent::LMarg << "attributes: " << endl ;
250 DapIndent::Indent() ;
251
252 if (d_attributes)
253 d_attributes->dump(strm);
254 else
255 d_attr.dump(strm) ;
256
257 DapIndent::UnIndent() ;
258
259 DapIndent::UnIndent() ;
260}
261
264string
266{
267 return d_name;
268}
269
276string
278{
279 if (get_parent() == 0)
280 return name();
281 else if (get_parent()->type() == dods_group_c)
282 return get_parent()->FQN() + name();
283 else
284 return get_parent()->FQN() + "." + name();
285}
286
288void
289BaseType::set_name(const string &n)
290{
291 string name = n;
292 d_name = www2id(name); // www2id writes into its param.
293}
294
302string
304{
305 return d_dataset;
306}
307
309Type
311{
312 return d_type;
313}
314
316void
318{
319 d_type = t;
320}
321
323string
325{
326 if (is_dap4())
327 return libdap::D4type_name(d_type);
328 else
329 return libdap::D2type_name(d_type);
330}
331
337bool
339{
341}
342
346bool
348{
350}
351
356bool
358{
360}
361
387int
389{
390 return 1;
391}
392
396bool
398{
399 return d_is_synthesized;
400}
401
407void
409{
410 d_is_synthesized = state;
411}
412
413// Return the state of d_is_read (true if the value of the variable has been
414// read (and is in memory) false otherwise).
415
424bool
426{
427 return d_is_read;
428}
429
460void
462{
463 // The this comment is/was wrong!
464 // The is_synthesized property was not being used and the more I thought
465 // about how this was coded, the more this code below seemed like a bad idea.
466 // Once the property was set, the read_p property could not be changed.
467 // That seems a little silly. Also, I think I need to use this is_synthesized
468 // property for some of the server function code I'm working on for Raytheon,
469 // and I'd like to be able to control the read_p property! jhrg 3/9/15
470
471 // What's true: The is_synthesized property is used by
472 // 'projection functions' in the freeform handler. It might be better
473 // to modify the FFtypes to support this behavior, but for now I'm returning
474 // the library to its old behavior. That this change (setting is_read
475 // of the value of is_syn...) broke the FF handler was not detected
476 // because the FF tests were not being run due to an error in the FF
477 // bes-testsuite Makefile.am). jhrg 9/9/15
478
479#if 1
480 if (!d_is_synthesized) {
481 d_is_read = state;
482 }
483#else
484 d_is_read = state;
485#endif
486}
487
498bool
500{
501 return d_is_send;
502}
503
512void
514{
515 DBG2(cerr << "Calling BaseType::set_send_p() for: " << this->name()
516 << endl);
517 d_is_send = state;
518}
519
520
526AttrTable &
528{
529 return d_attr;
530}
531
534void
536{
537 d_attr = at;
538}
539
545{
546 if (!d_attributes) d_attributes = new D4Attributes();
547 return d_attributes;
548}
549
550void
551BaseType::set_attributes(D4Attributes *attrs)
552{
553 d_attributes = new D4Attributes(*attrs);
554}
555
556void
557BaseType::set_attributes_nocopy(D4Attributes *attrs)
558{
559 d_attributes = attrs;
560}
562
590 AttrTable *at = at_container->get_attr_table(name());
591
592 DBG(cerr << "In BaseType::transfer_attributes; processing " << name() << endl);
593
594 if (at) {
595 at->set_is_global_attribute(false);
596 DBG(cerr << "Processing AttrTable: " << at->get_name() << endl);
597
598 AttrTable::Attr_iter at_p = at->attr_begin();
599 while (at_p != at->attr_end()) {
600 DBG(cerr << "About to append " << "attr name, type:" << at->get_name(at_p) << ", " << at->get_type(at_p) << endl);
601
602 if (at->get_attr_type(at_p) == Attr_container)
604 else
605 get_attr_table().append_attr(at->get_name(at_p), at->get_type(at_p), at->get_attr_vector(at_p));
606
607 at_p++;
608 }
609 }
610}
611
623bool
625{
626 return d_in_selection;
627}
628
638void
640{
641 d_in_selection = state;
642}
643
644// Protected method.
653void
655{
656 if (!dynamic_cast<Constructor *>(parent)
657 && !dynamic_cast<Vector *>(parent)
658 && parent != 0)
659 throw InternalErr("Call to set_parent with incorrect variable type.");
660
661 d_parent = parent;
662}
663
664// Public method.
665
671BaseType *
673{
674 return d_parent;
675}
676
677// Documented in the header file.
678BaseType *
679BaseType::var(const string &/*name*/, bool /*exact_match*/, btp_stack */*s*/)
680{
681 return static_cast<BaseType *>(0);
682}
683
700BaseType *
701BaseType::var(const string &, btp_stack &)
702{
703 return static_cast<BaseType *>(0);
704}
705
735void
737{
738 throw InternalErr(__FILE__, __LINE__, "BaseType::add_var unimplemented");
739}
740
741void
742BaseType::add_var_nocopy(BaseType *, Part)
743{
744 throw InternalErr(__FILE__, __LINE__, "BaseType::add_var_nocopy unimplemented");
745}
746
819bool
821{
822 if (d_is_read)
823 return true;
824
825 throw InternalErr("Unimplemented BaseType::read() method called for the variable named: " + name());
826}
827
828void
830{
831#if USE_LOCAL_TIMEOUT_SCHEME
832 dds.timeout_on();
833#endif
834 DBG2(cerr << "BaseType::intern_data: " << name() << endl);
835 if (!read_p())
836 read(); // read() throws Error and InternalErr
837#if USE_LOCAL_TIMEOUT_SCHEME
838 dds.timeout_off();
839#endif
840}
841
847void
848BaseType::intern_data(/*Crc32 &checksum, DMR &, ConstraintEvaluator &*/)
849{
850 if (!read_p())
851 read(); // read() throws Error and InternalErr
852#if 0
853 compute_checksum(checksum);
854#endif
855}
856
857bool
859{
860 throw InternalErr(__FILE__, __LINE__, "The DAP2 serialize() method has not been implemented for " + type_name());
861}
862
863bool
865{
866 throw InternalErr(__FILE__, __LINE__, "The DAP2 deserialize() method has not been implemented for " + type_name());
867}
868
869void
870BaseType::serialize(D4StreamMarshaller &, DMR &, /*ConstraintEvaluator &,*/ bool)
871{
872 throw InternalErr(__FILE__, __LINE__, "The DAP4 serialize() method has not been implemented for " + type_name());
873}
874
875void
877{
878 throw InternalErr(__FILE__, __LINE__, "The DAP4 deserialize() method has not been implemented for " + type_name());
879}
880
923void
924BaseType::print_decl(FILE *out, string space, bool print_semi,
925 bool constraint_info, bool constrained)
926{
927 ostringstream oss;
928 print_decl(oss, space, print_semi, constraint_info, constrained);
929 fwrite(oss.str().data(), sizeof(char), oss.str().length(), out);
930}
931
974void
975BaseType::print_decl(ostream &out, string space, bool print_semi,
976 bool constraint_info, bool constrained)
977{
978 // if printing the constrained declaration, exit if this variable was not
979 // selected.
980 if (constrained && !send_p())
981 return;
982
983 out << space << type_name() << " " << id2www(name()) ;
984
985 if (constraint_info) {
986 if (send_p())
987 out << ": Send True" ;
988 else
989 out << ": Send False" ;
990 }
991
992 if (print_semi)
993 out << ";\n" ;
994}
995
1010void
1011BaseType::print_val(FILE *out, string space, bool print_decl_p)
1012{
1013 ostringstream oss;
1014 print_val(oss, space, print_decl_p);
1015 fwrite(oss.str().data(), sizeof(char), oss.str().length(), out);
1016}
1017
1025void
1026BaseType::print_xml(FILE *out, string space, bool constrained)
1027{
1028 XMLWriter xml(space);
1029 print_xml_writer(xml, constrained);
1030 fwrite(xml.get_doc(), sizeof(char), xml.get_doc_size(), out);
1031}
1032
1040void
1041BaseType::print_xml(ostream &out, string space, bool constrained)
1042{
1043 XMLWriter xml(space);
1044 print_xml_writer(xml, constrained);
1045 out << xml.get_doc();
1046}
1047
1054void
1056{
1057 if (constrained && !send_p())
1058 return;
1059
1060 if (xmlTextWriterStartElement(xml.get_writer(), (const xmlChar*)type_name().c_str()) < 0)
1061 throw InternalErr(__FILE__, __LINE__, "Could not write " + type_name() + " element");
1062
1063 if (!name().empty())
1064 if (xmlTextWriterWriteAttribute(xml.get_writer(), (const xmlChar*) "name", (const xmlChar*)name().c_str()) < 0)
1065 throw InternalErr(__FILE__, __LINE__, "Could not write attribute for name");
1066
1067 if (is_dap4())
1068 attributes()->print_dap4(xml);
1069
1070 if (!is_dap4() && get_attr_table().get_size() > 0)
1072
1073 if (xmlTextWriterEndElement(xml.get_writer()) < 0)
1074 throw InternalErr(__FILE__, __LINE__, "Could not end " + type_name() + " element");
1075}
1076
1084void
1085BaseType::print_dap4(XMLWriter &xml, bool constrained)
1086{
1087 print_xml_writer(xml, constrained);
1088}
1089
1090// Compares the object's current state with the semantics of a particular
1091// type. This will typically be defined in ctor classes (which have
1092// complicated semantics). For BaseType, an object is semantically correct if
1093// it has both a non-null name and type.
1094//
1095// NB: This is not the same as an invariant -- during the parse objects exist
1096// but have no name. Also, the bool ALL defaults to false for BaseType. It is
1097// used by children of CtorType.
1098//
1099// Returns: true if the object is semantically correct, false otherwise.
1100
1129bool
1131{
1132 bool sem = (d_type != dods_null_c && name().length());
1133
1134 if (!sem)
1135 msg = "Every variable must have both a name and a type\n";
1136
1137 return sem;
1138}
1139
1176bool
1178{
1179 // Even though ops is a public method, it can never be called because
1180 // they will never have a BaseType object since this class is abstract,
1181 // however any of the child classes could by mistake call BaseType::ops
1182 // so this is an internal error. Jose Garcia
1183 throw InternalErr(__FILE__, __LINE__, "Unimplemented operator.");
1184}
1185
1202bool
1204{
1205 throw InternalErr(__FILE__, __LINE__, "Unimplemented operator.");
1206}
1207
1221unsigned int
1222BaseType::width(bool /* constrained */) const
1223{
1224 throw InternalErr(__FILE__, __LINE__, "not implemented");
1225#if 0
1226 return width(constrained);
1227#endif
1228}
1229
1230} // namespace libdap
Contains the attributes for a dataset.
Definition: AttrTable.h:143
virtual AttrTable * append_container(const string &name)
Add a container to the attribute table.
Definition: AttrTable.cc:409
virtual AttrTable * get_attr_table(const string &name)
Get an attribute container.
Definition: AttrTable.cc:606
virtual Attr_iter attr_end()
Definition: AttrTable.cc:718
virtual string get_type(const string &name)
Get the type name of an attribute within this attribute table.
Definition: AttrTable.cc:612
virtual vector< string > * get_attr_vector(const string &name)
Get a vector-valued attribute.
Definition: AttrTable.cc:652
virtual unsigned int append_attr(const string &name, const string &type, const string &value)
Add an attribute to the table.
Definition: AttrTable.cc:306
virtual Attr_iter attr_begin()
Definition: AttrTable.cc:710
virtual string get_name() const
Get the name of this attribute table.
Definition: AttrTable.cc:237
void print_xml_writer(XMLWriter &xml)
Definition: AttrTable.cc:1424
virtual void dump(ostream &strm) const
dumps information about this object
Definition: AttrTable.cc:1509
virtual AttrType get_attr_type(const string &name)
Get the type of an attribute.
Definition: AttrTable.cc:620
The basic data type for the DODS DAP types.
Definition: BaseType.h:118
void m_duplicate(const BaseType &bt)
Perform a deep copy.
Definition: BaseType.cc:85
virtual void print_xml_writer(XMLWriter &xml, bool constrained=false)
Definition: BaseType.cc:1055
virtual string type_name() const
Returns the type of the class instance as a string.
Definition: BaseType.cc:324
virtual void intern_data()
Read data into this variable.
Definition: BaseType.cc:848
virtual bool read()
Read data into a local buffer.
Definition: BaseType.cc:820
virtual bool deserialize(UnMarshaller &um, DDS *dds, bool reuse=false)
Receive data from the net.
Definition: BaseType.cc:864
virtual AttrTable & get_attr_table()
Definition: BaseType.cc:527
virtual string name() const
Returns the name of the class instance.
Definition: BaseType.cc:265
virtual void set_in_selection(bool state)
Definition: BaseType.cc:639
virtual void print_decl(FILE *out, string space=" ", bool print_semi=true, bool constraint_info=false, bool constrained=false)
Print an ASCII representation of the variable structure.
Definition: BaseType.cc:924
virtual BaseType * get_parent() const
Definition: BaseType.cc:672
virtual bool read_p()
Has this variable been read?
Definition: BaseType.cc:425
virtual unsigned int width(bool constrained=false) const
How many bytes does this use Return the number of bytes of storage this variable uses....
Definition: BaseType.cc:1222
virtual void set_read_p(bool state)
Sets the value of the read_p property.
Definition: BaseType.cc:461
virtual string dataset() const
Returns the name of the dataset used to create this instance.
Definition: BaseType.cc:303
virtual BaseType * var(const string &name="", bool exact_match=true, btp_stack *s=0)
Returns a pointer to a member of a constructor class.
Definition: BaseType.cc:679
virtual bool d4_ops(BaseType *b, int op)
Evaluator a relop for DAP4.
Definition: BaseType.cc:1203
virtual void set_attr_table(const AttrTable &at)
Definition: BaseType.cc:535
virtual void set_synthesized_p(bool state)
Definition: BaseType.cc:408
virtual void set_parent(BaseType *parent)
Definition: BaseType.cc:654
virtual int element_count(bool leaves=false)
Count the members of constructor types.
Definition: BaseType.cc:388
virtual string toString()
Definition: BaseType.cc:183
virtual bool is_vector_type() const
Returns true if the instance is a vector (i.e., array) type variable.
Definition: BaseType.cc:347
virtual BaseType * transform_to_dap4(D4Group *root, Constructor *container)
DAP2 to DAP4 transform.
Definition: BaseType.cc:215
virtual void print_xml(FILE *out, string space=" ", bool constrained=false)
Definition: BaseType.cc:1026
virtual void set_name(const string &n)
Sets the name of the class instance.
Definition: BaseType.cc:289
virtual bool ops(BaseType *b, int op)
Evaluate relational operators.
Definition: BaseType.cc:1177
virtual bool is_constructor_type() const
Returns true if the instance is a constructor (i.e., Structure, Sequence or Grid) type variable.
Definition: BaseType.cc:357
virtual D4Attributes * attributes()
Definition: BaseType.cc:544
virtual std::string FQN() const
Definition: BaseType.cc:277
virtual bool send_p()
Should this variable be sent?
Definition: BaseType.cc:499
virtual bool is_simple_type() const
Returns true if the instance is a numeric, string or URL type variable.
Definition: BaseType.cc:338
virtual void set_send_p(bool state)
Definition: BaseType.cc:513
virtual BaseType * ptr_duplicate()=0
virtual void compute_checksum(Crc32 &checksum)=0
include the data for this variable in the checksum DAP4 includes a checksum with every data response....
virtual bool serialize(ConstraintEvaluator &eval, DDS &dds, Marshaller &m, bool ce_eval=true)
Move data to the net, then remove them from the object.
Definition: BaseType.cc:858
virtual void add_var(BaseType *bt, Part part=nil)
Add a variable.
Definition: BaseType.cc:736
virtual void transfer_attributes(AttrTable *at)
Definition: BaseType.cc:589
virtual void dump(ostream &strm) const
dumps information about this object
Definition: BaseType.cc:236
virtual bool is_in_selection()
Is this variable part of the current selection?
Definition: BaseType.cc:624
virtual bool synthesized_p()
Definition: BaseType.cc:397
virtual bool check_semantics(string &msg, bool all=false)
Compare an object's current state with the semantics of its type.
Definition: BaseType.cc:1130
BaseType(const string &n, const Type &t, bool is_dap4=false)
The BaseType constructor.
Definition: BaseType.cc:125
virtual void set_type(const Type &t)
Sets the type of the class instance.
Definition: BaseType.cc:317
virtual Type type() const
Returns the type of the class instance.
Definition: BaseType.cc:310
virtual void print_val(FILE *out, string space="", bool print_decl_p=true)
Prints the value of the variable.
Definition: BaseType.cc:1011
virtual void print_dap4(XMLWriter &xml, bool constrained=false)
Definition: BaseType.cc:1085
Evaluate a constraint expression.
void transform_to_dap4(AttrTable &at)
copy attributes from DAP2 to DAP4
virtual void dump(ostream &strm) const
dumps information about this object
Marshaller that knows how to marshal/serialize dap data objects to a C++ iostream using DAP4's receiv...
Read data from the stream made by D4StreamMarshaller.
libdap base object for common functionality of libdap objects
Definition: DapObj.h:56
A class for software fault reporting.
Definition: InternalErr.h:65
abstract base class used to marshal/serialize dap data objects
Definition: Marshaller.h:50
abstract base class used to unmarshall/deserialize dap data objects
Definition: UnMarshaller.h:55
Holds a one-dimensional collection of DAP2 data types.
Definition: Vector.h:81
Type
Identifies the data type.
Definition: Type.h:94
string www2id(const string &in, const string &escape, const string &except)
Definition: escaping.cc:220
bool is_simple_type(Type t)
Returns true if the instance is a numeric, string or URL type variable.
Definition: util.cc:771
string D2type_name(Type t)
Returns the type of the class instance as a string. Supports all DAP2 types and not the DAP4-only typ...
Definition: util.cc:645
string D4type_name(Type t)
Returns the type of the class instance as a string. Supports all DAP4 types and not the DAP2-only typ...
Definition: util.cc:690
bool is_constructor_type(Type t)
Returns true if the instance is a constructor (i.e., Structure, Sequence or Grid) type variable.
Definition: util.cc:859
bool is_vector_type(Type t)
Returns true if the instance is a vector (i.e., array) type variable.
Definition: util.cc:813
Part
Names the parts of multi-section constructor data types.
Definition: Type.h:48
string id2www(string in, const string &allowable)
Definition: escaping.cc:153