20 #include "asterisk/res_geolocation.h"
21 #include "geoloc_private.h"
25 enum geoloc_shape_attrs {
26 GEOLOC_SHAPE_ATTR_POS = 0,
27 GEOLOC_SHAPE_ATTR_POS3D,
28 GEOLOC_SHAPE_ATTR_RADIUS,
29 GEOLOC_SHAPE_ATTR_SEMI_MAJOR_AXIS,
30 GEOLOC_SHAPE_ATTR_SEMI_MINOR_AXIS,
31 GEOLOC_SHAPE_ATTR_VERTICAL_AXIS,
32 GEOLOC_SHAPE_ATTR_HEIGHT,
33 GEOLOC_SHAPE_ATTR_ORIENTATION,
34 GEOLOC_SHAPE_ATTR_ORIENTATION_UOM,
35 GEOLOC_SHAPE_ATTR_INNER_RADIUS,
36 GEOLOC_SHAPE_ATTR_OUTER_RADIUS,
37 GEOLOC_SHAPE_ATTR_STARTING_ANGLE,
38 GEOLOC_SHAPE_ATTR_OPENING_ANGLE,
39 GEOLOC_SHAPE_ATTR_ANGLE_UOM,
43 enum geoloc_shape_attrs attr;
45 int (*validator)(
const char *value);
50 { GEOLOC_SHAPE_ATTR_POS,
"pos", NULL, NULL},
51 { GEOLOC_SHAPE_ATTR_POS3D,
"pos3d", NULL, NULL},
52 { GEOLOC_SHAPE_ATTR_RADIUS,
"radius", NULL, NULL},
53 { GEOLOC_SHAPE_ATTR_SEMI_MAJOR_AXIS,
"semiMajorAxis", NULL, NULL},
54 { GEOLOC_SHAPE_ATTR_SEMI_MINOR_AXIS,
"semiMinorAxis", NULL, NULL},
55 { GEOLOC_SHAPE_ATTR_VERTICAL_AXIS,
"verticalAxis", NULL, NULL},
56 { GEOLOC_SHAPE_ATTR_HEIGHT,
"height", NULL, NULL},
57 { GEOLOC_SHAPE_ATTR_ORIENTATION,
"orientation", NULL, NULL},
58 { GEOLOC_SHAPE_ATTR_ORIENTATION_UOM,
"orientation_uom", NULL, NULL},
59 { GEOLOC_SHAPE_ATTR_INNER_RADIUS,
"innerRadius", NULL, NULL},
60 { GEOLOC_SHAPE_ATTR_OUTER_RADIUS,
"outerRadius", NULL, NULL},
61 { GEOLOC_SHAPE_ATTR_STARTING_ANGLE,
"startingAngle", NULL, NULL},
62 { GEOLOC_SHAPE_ATTR_OPENING_ANGLE,
"openingAngle", NULL, NULL},
63 { GEOLOC_SHAPE_ATTR_ANGLE_UOM,
"angle_uom", NULL, NULL},
65 #endif //not used yet.
68 const char *attribute;
71 int (*validator)(
const char *value);
75 const char *shape_type;
79 static int pos_validator(
const char *value)
83 return (sscanf(value,
"%f %f", &lat, &lon) == 2);
86 static int pos3d_validator(
const char *value)
91 return (sscanf(value,
"%f %f %f", &lat, &lon, &alt) == 3);
94 static int float_validator(
const char *value)
97 return (sscanf(value,
"%f", &val) == 1);
100 static int uom_validator(
const char *value)
107 {
"Point", { {
"pos", 1, 1, pos_validator}, {NULL, -1, -1} }},
108 {
"Polygon", { {
"pos", 3, -1, pos_validator}, {NULL, -1, -1} }},
109 {
"Circle", { {
"pos", 1, 1, pos_validator}, {
"radius", 1, 1, float_validator},{NULL, -1, -1}}},
110 {
"Ellipse", { {
"pos", 1, 1, pos_validator}, {
"semiMajorAxis", 1, 1, float_validator},
111 {
"semiMinorAxis", 1, 1, float_validator}, {
"orientation", 1, 1, float_validator},
112 {
"orientation_uom", 1, 1, uom_validator}, {NULL, -1, -1} }},
113 {
"ArcBand", { {
"pos", 1, 1, pos_validator}, {
"innerRadius", 1, 1, float_validator},
114 {
"outerRadius", 1, 1, float_validator}, {
"startAngle", 1, 1, float_validator},
115 {
"startAngle_uom", 1, 1, uom_validator}, {
"openingAngle", 1, 1, float_validator},
116 {
"openingAngle_uom", 1, 1, uom_validator}, {NULL, -1, -1} }},
117 {
"Sphere", { {
"pos3d", 1, 1, pos3d_validator}, {
"radius", 1, 1, float_validator}, {NULL, -1, -1} }},
118 {
"Ellipse", { {
"pos3d", 1, 1, pos3d_validator}, {
"semiMajorAxis", 1, 1, float_validator},
119 {
"semiMinorAxis", 1, 1, float_validator}, {
"verticalAxis", 1, 1, float_validator},
120 {
"orientation", 1, 1, float_validator}, {
"orientation_uom", 1, 1, uom_validator}, {NULL, -1, -1} }},
121 {
"Prism", { {
"pos3d", 3, -1, pos_validator}, {
"height", 1, 1, float_validator}, {NULL, -1, -1} }},
124 enum ast_geoloc_validate_result ast_geoloc_gml_validate_varlist(
const struct ast_variable *varlist,
133 return AST_GEOLOC_VALIDATE_MISSING_SHAPE;
136 for (i = 0; i < ARRAY_LEN(gml_shape_defs); i++) {
142 return AST_GEOLOC_VALIDATE_INVALID_SHAPE;
145 for (var = varlist; var; var = var->
next) {
146 int vname_index = -1;
150 for (i = 0; i < ARRAY_LEN(gml_shape_defs[def_index].required_attributes); i++) {
151 if (gml_shape_defs[def_index].required_attributes[i].attribute == NULL) {
159 if (vname_index < 0) {
161 return AST_GEOLOC_VALIDATE_INVALID_VARNAME;
163 if (!gml_shape_defs[def_index].required_attributes[vname_index].validator(var->
value)) {
165 return AST_GEOLOC_VALIDATE_INVALID_VALUE;
169 for (i = 0; i < ARRAY_LEN(gml_shape_defs[def_index].required_attributes); i++) {
171 if (gml_shape_defs[def_index].required_attributes[i].attribute == NULL) {
175 for (var = varlist; var; var = var->
next) {
180 if (count < gml_shape_defs[def_index].required_attributes[i].min_required) {
181 *result = gml_shape_defs[def_index].required_attributes[i].attribute;
182 return AST_GEOLOC_VALIDATE_NOT_ENOUGH_VARNAMES;
184 if (gml_shape_defs[def_index].required_attributes[i].max_allowed > 0 &&
185 count > gml_shape_defs[def_index].required_attributes[i].max_allowed) {
186 *result = gml_shape_defs[def_index].required_attributes[i].attribute;
187 return AST_GEOLOC_VALIDATE_TOO_MANY_VARNAMES;
190 return AST_GEOLOC_VALIDATE_SUCCESS;
199 e->
command =
"geoloc show gml_shape_defs";
201 "Usage: geoloc show gml_shape_defs\n"
202 " Show the GML Shape definitions.\n";
208 ast_cli(a->fd,
"%-16s %-32s\n",
"Shape",
"Attributes name(min,max)");
209 ast_cli(a->fd,
"================ ===============================\n");
211 for (i = 0; i < ARRAY_LEN(gml_shape_defs); i++) {
213 ast_cli(a->fd,
"%-16s", gml_shape_defs[i].shape_type);
214 for (j = 0; j < ARRAY_LEN(gml_shape_defs[i].required_attributes); j++) {
215 if (gml_shape_defs[i].required_attributes[j].attribute == NULL) {
218 if (gml_shape_defs[i].required_attributes[j].max_allowed >= 0) {
219 ast_cli(a->fd,
" %s(%d,%d)", gml_shape_defs[i].required_attributes[j].attribute,
220 gml_shape_defs[i].required_attributes[j].min_required,
221 gml_shape_defs[i].required_attributes[j].max_allowed);
223 ast_cli(a->fd,
" %s(%d,unl)", gml_shape_defs[i].required_attributes[j].attribute,
224 gml_shape_defs[i].required_attributes[j].min_required);
227 ast_cli(a->fd,
"\n");
229 ast_cli(a->fd,
"\n");
235 AST_CLI_DEFINE(handle_gml_show,
"Show the GML Shape definitions"),
238 struct ast_xml_node *geoloc_gml_list_to_xml(
const struct ast_variable *resolved_location,
239 const char *ref_string)
244 struct ast_xml_node *gml_node;
245 struct ast_xml_node *child_node;
248 SCOPE_ENTER(3,
"%s", ref_string);
250 if (!resolved_location) {
251 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: resolved_location was NULL\n",
256 if (ast_strlen_zero(shape)) {
257 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: There's no 'shape' parameter\n",
261 if (ast_strlen_zero(crs)) {
267 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: Unable to create '%s' XML node\n", shape, ref_string);
272 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: Unable to create 'crs' XML attribute\n", ref_string);
275 for (var = (
struct ast_variable *)resolved_location; var; var = var->
next) {
276 RAII_VAR(
char *, value, NULL, ast_free);
292 a = strsep(&uom,
" ");
293 angle = strtof(a, &junk);
300 if (!ast_strlen_zero(junk)) {
302 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: The angle portion of parameter '%s' ('%s') is malformed\n",
306 if (ast_strlen_zero(uom)) {
313 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: Parameter '%s': '%s' is malformed. "
314 "Degrees can't be > 360.0\n",
320 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: Parameter '%s': '%s' is malformed. "
321 "Radians can't be > 100.0\n",
326 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: Parameter '%s': '%s' is malformed. "
327 "The unit of measure must be 'deg[rees]' or 'rad[ians]'\n",
335 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: Unable to create '%s' XML node\n", var->
name, ref_string);
337 if (!ast_strlen_zero(uom)) {
341 SCOPE_EXIT_LOG_RTN_VALUE(NULL, LOG_ERROR,
"%s: Unable to create 'uom' XML attribute\n", ref_string);
347 SCOPE_EXIT_RTN_VALUE(gml_node,
"%s: Done\n", ref_string);
350 int geoloc_gml_unload(
void)
357 int geoloc_gml_load(
void)
364 int geoloc_gml_reload(
void)
struct ast_variable * next
Asterisk main include file. File version handling, generic pbx functions.
int ast_cli_unregister_multiple(struct ast_cli_entry *e, int len)
Unregister multiple commands.
descriptor for a cli entry.
void ast_xml_free_node(struct ast_xml_node *node)
Free node.
Structure for variables, used for configurations and for channel variables.
#define ast_cli_register_multiple(e, len)
Register multiple commands.
#define ast_strdup(str)
A wrapper for strdup()
struct ast_xml_node * ast_xml_new_child(struct ast_xml_node *parent, const char *child_name)
Add a child node inside a passed parent node.
Configuration File Parser.
const char * ast_variable_find_in_list(const struct ast_variable *list, const char *variable)
Gets the value of a variable from a variable list by name.
struct ast_xml_node * ast_xml_new_node(const char *name)
Create a XML node.
int ast_strings_equal(const char *str1, const char *str2)
Compare strings for equality checking for NULL.
void ast_xml_set_text(struct ast_xml_node *node, const char *content)
Set an element content string.
int ast_xml_set_attribute(struct ast_xml_node *node, const char *name, const char *value)
Set an attribute to a node.
Standard Command Line Interface.
static int force_inline attribute_pure ast_begins_with(const char *str, const char *prefix)
Checks whether a string begins with another.
#define RAII_VAR(vartype, varname, initval, dtor)
Declare a variable that will call a destructor function when it goes out of scope.