1 #include "ngspice/ngspice.h"
2 #include "ngspice/dvec.h"
3
4
dvec_alloc(char * name,int type,short flags,int length,void * storage)5 struct dvec *dvec_alloc(/* NOT const -- assigned to char */ char *name,
6 int type, short flags, int length, void *storage)
7 {
8 struct dvec * const rv = TMALLOC(struct dvec, 1);
9
10 /* If the allocation failed, return NULL as a failure flag.
11 * As of 2019-03, TMALLOC will not return on failure, so this check is
12 * redundant, but it may be useful if it is decided to allow the
13 * allocation functions to return NULL on failure and handle recovery
14 * by the calling functions */
15 if (!rv) {
16 return NULL;
17 }
18
19 /* Set all fields to 0 */
20 ZERO(rv, struct dvec);
21
22 /* Set information on the vector from parameters. Note that storage for
23 * the name string belongs to the dvec when this function returns. */
24 rv->v_name = name;
25 rv->v_type = type;
26 rv->v_flags = flags;
27 rv->v_length = length;
28 rv->v_alloc_length = length;
29 rv->v_numdims = 1; /* Assume 1 D */
30 rv->v_dims[0] = length;
31
32 if (length == 0) { /* Redundant due to ZERO() call above */
33 rv->v_realdata = NULL;
34 rv->v_compdata = NULL;
35 }
36 else if (flags & VF_REAL) {
37 /* Vector consists of real data. Use the supplied storage if given
38 * or allocate if not */
39 rv->v_realdata = storage
40 ? (double *) storage
41 : TMALLOC(double, length);
42 rv->v_compdata = NULL;
43 }
44 else if (flags & VF_COMPLEX) {
45 /* Vector holds complex data. Perform actions as for real data */
46 rv->v_realdata = NULL;
47 rv->v_compdata = storage
48 ? (ngcomplex_t *) storage
49 : TMALLOC(ngcomplex_t, length);
50 }
51
52 /* Set remaining fields to none/unknown. Again not required due to
53 * the ZERO() call */
54 rv->v_plot = NULL;
55 rv->v_scale = NULL;
56
57 return rv;
58 } /* end of function dvec_alloc */
59
60
61 /* Resize dvec to length if storage is NULL orr replace
62 * its existing allocation with storage if not
63 */
dvec_realloc(struct dvec * v,int length,void * storage)64 void dvec_realloc(struct dvec *v, int length, void *storage)
65 {
66 if (isreal(v)) {
67 if (storage) {
68 tfree(v->v_realdata);
69 v->v_realdata = (double *) storage;
70 }
71 else {
72 v->v_realdata = TREALLOC(double, v->v_realdata, length);
73 }
74 }
75 else {
76 if (storage) {
77 tfree(v->v_compdata);
78 v->v_compdata = (ngcomplex_t *) storage;
79 }
80 else {
81 v->v_compdata = TREALLOC(ngcomplex_t, v->v_compdata, length);
82 }
83 }
84
85 v->v_length = length;
86 v->v_alloc_length = length;
87 } /* end of function dvec_realloc */
88
89
dvec_extend(struct dvec * v,int length)90 void dvec_extend(struct dvec *v, int length)
91 {
92 if (isreal(v)) {
93 v->v_realdata = TREALLOC(double, v->v_realdata, length);
94 }
95 else {
96 v->v_compdata = TREALLOC(ngcomplex_t, v->v_compdata, length);
97 }
98
99 v->v_alloc_length = length;
100 } /* end of function dvec_extend */
101
102
103
dvec_trunc(struct dvec * v,int length)104 void dvec_trunc(struct dvec *v, int length)
105 {
106 /* Ensure valid */
107 if (v->v_alloc_length <= length) {
108 v->v_length = length;
109 }
110 } /* end of function dvec_trunc */
111
112
113
dvec_free(struct dvec * v)114 void dvec_free(struct dvec *v)
115 {
116 /* Check for freed vector */
117 if (v == (struct dvec *) NULL) {
118 return;
119 }
120
121 /* Free the various allocations */
122 if (v->v_name) {
123 txfree(v->v_name);
124 }
125 if (v->v_realdata) {
126 txfree(v->v_realdata);
127 }
128 else if (v->v_compdata) { /* if data real, not complex */
129 txfree(v->v_compdata);
130 }
131 txfree(v);
132 } /* end of function dvec_free */
133
134
135
136