1 /*
2 Copyright (c) 2000, 2015, Oracle and/or its affiliates.
3 Copyright (c) 2009, 2019, MariaDB
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; version 2 of the License.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
17
18 #include <my_global.h>
19 #include <sql_class.h> // THD
20 #include <sql_i_s.h> // ST_SCHEMA_TABLE
21 #include <mysql/plugin.h>
22 #include "sql_show.h" // get_all_tables()
23 #include "sql_error.h" // convert_error_to_warning()
24 #include "sql_type_geom.h"
25
26
27 /*********** INFORMATION_SCHEMA.SPATIEL_REF_SYS *******************/
28
29 namespace Show {
30
31 static ST_FIELD_INFO spatial_ref_sys_fields_info[]=
32 {
33 Column("SRID", SShort(5), NOT_NULL),
34 Column("AUTH_NAME", Varchar(FN_REFLEN), NOT_NULL),
35 Column("AUTH_SRID", SLong(5), NOT_NULL),
36 Column("SRTEXT", Varchar(2048), NOT_NULL),
37 CEnd()
38 };
39
40
spatial_ref_sys_fill(THD * thd,TABLE_LIST * tables,COND * cond)41 static int spatial_ref_sys_fill(THD *thd, TABLE_LIST *tables, COND *cond)
42 {
43 DBUG_ENTER("fill_spatial_ref_sys");
44 TABLE *table= tables->table;
45 CHARSET_INFO *cs= system_charset_info;
46 int result= 1;
47
48 restore_record(table, s->default_values);
49
50 table->field[0]->store(-1, FALSE); /*SRID*/
51 table->field[1]->store(STRING_WITH_LEN("Not defined"), cs); /*AUTH_NAME*/
52 table->field[2]->store(-1, FALSE); /*AUTH_SRID*/
53 table->field[3]->store(STRING_WITH_LEN(
54 "LOCAL_CS[\"Spatial reference wasn't specified\","
55 "LOCAL_DATUM[\"Unknown\",0]," "UNIT[\"m\",1.0]," "AXIS[\"x\",EAST],"
56 "AXIS[\"y\",NORTH]]"), cs);/*SRTEXT*/
57 if (schema_table_store_record(thd, table))
58 goto exit;
59
60 table->field[0]->store(0, TRUE); /*SRID*/
61 table->field[1]->store(STRING_WITH_LEN("EPSG"), cs); /*AUTH_NAME*/
62 table->field[2]->store(404000, TRUE); /*AUTH_SRID*/
63 table->field[3]->store(STRING_WITH_LEN(
64 "LOCAL_CS[\"Wildcard 2D cartesian plane in metric unit\","
65 "LOCAL_DATUM[\"Unknown\",0]," "UNIT[\"m\",1.0],"
66 "AXIS[\"x\",EAST]," "AXIS[\"y\",NORTH],"
67 "AUTHORITY[\"EPSG\",\"404000\"]]"), cs);/*SRTEXT*/
68 if (schema_table_store_record(thd, table))
69 goto exit;
70
71 result= 0;
72
73 exit:
74 DBUG_RETURN(result);
75 }
76
77
plugin_init_spatial_ref_sys(void * p)78 static int plugin_init_spatial_ref_sys(void *p)
79 {
80 ST_SCHEMA_TABLE *schema= (ST_SCHEMA_TABLE *)p;
81 schema->fields_info= spatial_ref_sys_fields_info;
82 schema->fill_table= spatial_ref_sys_fill;
83 return 0;
84 }
85
86
87 static struct st_mysql_information_schema spatial_ref_sys_plugin=
88 { MYSQL_INFORMATION_SCHEMA_INTERFACE_VERSION };
89
90
91 } // namespace Show
92
93 /*********** INFORMATION_SCHEMA.GEOMETRY_COLUMNS *******************/
94
95
96 namespace Show {
97
98 static ST_FIELD_INFO geometry_columns_fields_info[]=
99 {
100 Column("F_TABLE_CATALOG", Catalog(), NOT_NULL, OPEN_FRM_ONLY),
101 Column("F_TABLE_SCHEMA", Name(), NOT_NULL, OPEN_FRM_ONLY),
102 Column("F_TABLE_NAME", Name(), NOT_NULL, OPEN_FRM_ONLY),
103 Column("F_GEOMETRY_COLUMN", Name(), NOT_NULL, OPEN_FRM_ONLY),
104 Column("G_TABLE_CATALOG", Catalog(), NOT_NULL, OPEN_FRM_ONLY),
105 Column("G_TABLE_SCHEMA", Name(), NOT_NULL, OPEN_FRM_ONLY),
106 Column("G_TABLE_NAME", Name(), NOT_NULL, OPEN_FRM_ONLY),
107 Column("G_GEOMETRY_COLUMN", Name(), NOT_NULL, OPEN_FRM_ONLY),
108 Column("STORAGE_TYPE", STiny(2), NOT_NULL, OPEN_FRM_ONLY),
109 Column("GEOMETRY_TYPE", SLong(7), NOT_NULL, OPEN_FRM_ONLY),
110 Column("COORD_DIMENSION", STiny(2), NOT_NULL, OPEN_FRM_ONLY),
111 Column("MAX_PPR", STiny(2), NOT_NULL, OPEN_FRM_ONLY),
112 Column("SRID", SShort(5), NOT_NULL, OPEN_FRM_ONLY),
113 CEnd()
114 };
115
116
geometry_columns_fill_record(TABLE * table,const LEX_CSTRING * db_name,const LEX_CSTRING * table_name,const Field_geom * field)117 static void geometry_columns_fill_record(TABLE *table,
118 const LEX_CSTRING *db_name,
119 const LEX_CSTRING *table_name,
120 const Field_geom *field)
121 {
122 static const LEX_CSTRING catalog= {STRING_WITH_LEN("def")};
123 const CHARSET_INFO *cs= system_charset_info;
124 const Type_handler_geometry *gth= field->type_handler_geom();
125 /*F_TABLE_CATALOG*/
126 table->field[0]->store(catalog, cs);
127 /*F_TABLE_SCHEMA*/
128 table->field[1]->store(db_name, cs);
129 /*F_TABLE_NAME*/
130 table->field[2]->store(table_name, cs);
131 /*G_TABLE_CATALOG*/
132 table->field[4]->store(catalog, cs);
133 /*G_TABLE_SCHEMA*/
134 table->field[5]->store(db_name, cs);
135 /*G_TABLE_NAME*/
136 table->field[6]->store(table_name, cs);
137 /*G_GEOMETRY_COLUMN*/
138 table->field[7]->store(field->field_name, cs);
139 /*STORAGE_TYPE*/
140 table->field[8]->store(1LL, true); /*Always 1 (binary implementation)*/
141 /*GEOMETRY_TYPE*/
142 table->field[9]->store((longlong) (gth->geometry_type()), true);
143 /*COORD_DIMENSION*/
144 table->field[10]->store(2LL, true);
145 /*MAX_PPR*/
146 table->field[11]->set_null();
147 /*SRID*/
148 table->field[12]->store((longlong) (field->get_srid()), true);
149 }
150
151
get_geometry_column_record(THD * thd,TABLE_LIST * tables,TABLE * table,bool res,const LEX_CSTRING * db_name,const LEX_CSTRING * table_name)152 static int get_geometry_column_record(THD *thd, TABLE_LIST *tables,
153 TABLE *table, bool res,
154 const LEX_CSTRING *db_name,
155 const LEX_CSTRING *table_name)
156 {
157 TABLE *show_table;
158 Field **ptr, *field;
159 DBUG_ENTER("get_geometry_column_record");
160
161 if (res)
162 {
163 /*
164 open_table() failed with an error.
165 Convert the error to a warning and let the caller
166 continue with the next table.
167 */
168 convert_error_to_warning(thd);
169 DBUG_RETURN(0);
170 }
171
172 // Skip INFORMATION_SCHEMA tables. They don't have geometry columns.
173 if (tables->schema_table)
174 DBUG_RETURN(0);
175
176 show_table= tables->table;
177 ptr= show_table->field;
178 show_table->use_all_columns(); // Required for default
179 restore_record(show_table, s->default_values);
180
181 for (; (field= *ptr) ; ptr++)
182 {
183 const Field_geom *fg;
184 if (field->type() == MYSQL_TYPE_GEOMETRY &&
185 (fg= dynamic_cast<const Field_geom*>(field)))
186 {
187 DEBUG_SYNC(thd, "get_schema_column");
188 /* Get default row, with all NULL fields set to NULL */
189 restore_record(table, s->default_values);
190 geometry_columns_fill_record(table, db_name, table_name, fg);
191 if (schema_table_store_record(thd, table))
192 DBUG_RETURN(1);
193 }
194 }
195
196 DBUG_RETURN(0);
197 }
198
199
plugin_init_geometry_columns(void * p)200 static int plugin_init_geometry_columns(void *p)
201 {
202 ST_SCHEMA_TABLE *schema= (ST_SCHEMA_TABLE *)p;
203 schema->fields_info= geometry_columns_fields_info;
204 schema->fill_table= get_all_tables;
205 schema->process_table= get_geometry_column_record;
206 schema->idx_field1= 1;
207 schema->idx_field2= 2;
208 schema->i_s_requested_object= OPTIMIZE_I_S_TABLE | OPEN_VIEW_FULL;
209 return 0;
210 }
211
212
213 static struct st_mysql_information_schema geometry_columns_plugin=
214 { MYSQL_INFORMATION_SCHEMA_INTERFACE_VERSION };
215
216
217 } // namespace Show
218
219
220 /********************* Plugin library descriptors ************************/
221
222
maria_declare_plugin(type_geom)223 maria_declare_plugin(type_geom)
224 {
225 MYSQL_INFORMATION_SCHEMA_PLUGIN, // the plugin type (see include/mysql/plugin.h)
226 &Show::spatial_ref_sys_plugin, // pointer to type-specific plugin descriptor
227 "SPATIAL_REF_SYS", // plugin name
228 "MariaDB", // plugin author
229 "Lists all geometry columns", // the plugin description
230 PLUGIN_LICENSE_GPL, // the plugin license (see include/mysql/plugin.h)
231 Show::plugin_init_spatial_ref_sys, // Pointer to plugin initialization function
232 0, // Pointer to plugin deinitialization function
233 0x0100, // Numeric version 0xAABB means AA.BB version
234 NULL, // Status variables
235 NULL, // System variables
236 "1.0", // String version representation
237 MariaDB_PLUGIN_MATURITY_STABLE // Maturity (see include/mysql/plugin.h)*/
238 },
239 {
240 MYSQL_INFORMATION_SCHEMA_PLUGIN, // the plugin type (see include/mysql/plugin.h)
241 &Show::geometry_columns_plugin, // pointer to type-specific plugin descriptor
242 "GEOMETRY_COLUMNS", // plugin name
243 "MariaDB", // plugin author
244 "Lists all geometry columns", // the plugin description
245 PLUGIN_LICENSE_GPL, // the plugin license (see include/mysql/plugin.h)
246 Show::plugin_init_geometry_columns,// Pointer to plugin initialization function
247 0, // Pointer to plugin deinitialization function
248 0x0100, // Numeric version 0xAABB means AA.BB version
249 NULL, // Status variables
250 NULL, // System variables
251 "1.0", // String version representation
252 MariaDB_PLUGIN_MATURITY_STABLE // Maturity (see include/mysql/plugin.h)
253 }
254 maria_declare_plugin_end;
255