caddr_t bif_week (caddr_t * qst, caddr_t * err_ret, state_slot_t ** args) { caddr_t arg = bif_date_arg (qst, args, 0, "week"); TIMESTAMP_STRUCT ts; uint32 nowadays, new_year; dt_to_timestamp_struct (arg, &ts); nowadays = date2num (ts.year, ts.month, ts.day); new_year = date2num (ts.year, 1, 1); return (box_num ((nowadays - new_year) / 7 + 1)); }
caddr_t clr_deserialize (dk_session_t * ses, long mode, caddr_t asm_name, caddr_t type, void *udt) { MonoArray *v_args = NULL, *bin_data; MonoArray *mono_list; int len; caddr_t in_values, bin_data_ptr; MonoDomain *domain = virtuoso_domain; get_mono_thread (); in_values = (caddr_t) scan_session_boxing (ses); if (DV_TYPE_OF (in_values) != DV_BIN) return (caddr_t) box_num (0); len = box_length (in_values); bin_data = mono_array_new (domain, mono_get_byte_class(), len); bin_data_ptr = mono_array_addr (bin_data, char, 0); memcpy (bin_data_ptr, in_values, len); if (in_values) dk_free_tree (in_values); v_args = MAKE_PARAM_ARRAY (domain, 4); mono_array_set (v_args, gpointer, 0, bin_data); SET_INT_ARG (domain, v_args, 1, mode); SET_STRING_ARG (domain, v_args, 2, asm_name); SET_STRING_ARG (domain, v_args, 3, type); QR_RESET_CTX { mono_list = (MonoArray *) call_mono (VIRTCLR_NAME, "VInvoke:obj_deserialize", v_args, domain); } QR_RESET_CODE { caddr_t err; POP_QR_RESET; err = thr_get_error_code (THREAD_CURRENT_THREAD); if (ARRAYP (err)) log_error ("Mono Deserialization error : [%s] [%s]", ERR_STATE(err), ERR_MESSAGE (err)); else log_error ("Mono Deserialization error : unknown"); dk_free_tree (err); return 0; } END_QR_RESET; return sa_to_dk ((MonoArray *) mono_list, 0, 0, udt); }
void qst_set_long (caddr_t * state, state_slot_t * sl, boxint lv) { #ifdef QST_DEBUG if (sl->ssl_index < QI_FIRST_FREE) GPF_T1 ("Invalid SSL in qst_set"); else if (sl->ssl_type == SSL_CONSTANT) GPF_T1 ("Invalid constant SSL in qst_set"); else { #endif caddr_t *place = IS_SSL_REF_PARAMETER (sl->ssl_type) ? (caddr_t *) state[sl->ssl_index] : (caddr_t *) & state[sl->ssl_index]; caddr_t old = *place; if (IS_BOX_POINTER (old)) { if (DV_LONG_INT == box_tag (old)) { *(boxint *) old = lv; } else { ssl_free_data (sl, *place); *place = box_num (lv); } } else { if (IS_BOXINT_POINTER (lv)) *place = box_num (lv); else *(ptrlong *) place = lv; } #ifdef QST_DEBUG } #endif }
caddr_t bif_im_XY_to_Morton (caddr_t * qst, caddr_t * err, state_slot_t ** args) { int x = bif_long_range_arg (qst, args, 0, "IM XYtoMorton", 0, 0x7fffffff); int y = bif_long_range_arg (qst, args, 1, "IM XYtoMorton", 0, 0x7fffffff); int i = 0, morton = 0; while (x || y) { morton |= (x & 1) << (i++); morton |= (y & 1) << (i++); x >>= 1; y >>= 1; } return box_num (morton); }
caddr_t bif_quarter (caddr_t * qst, caddr_t * err_ret, state_slot_t ** args) { caddr_t arg = bif_date_arg (qst, args, 0, "quarter"); TIMESTAMP_STRUCT ts; int quarter; dt_to_timestamp_struct (arg, &ts); if (ts.month <= 3) quarter = 1; else if (ts.month <= 6) quarter = 2; else if (ts.month <= 9) quarter = 3; else quarter = 4; return (box_num (quarter)); }
caddr_t bif_timestampdiff (caddr_t * qst, caddr_t * err_ret, state_slot_t ** args) { ptrlong long_unit = bif_long_arg (qst, args, 0, "timestampdiff"); caddr_t dt1 = bif_date_arg (qst, args, 1, "timestampdiff"); caddr_t dt2 = bif_date_arg (qst, args, 2, "timestampdiff"); GMTIMESTAMP_STRUCT ts1, ts2; /* BELOW OVERFLOWS on 32 bit long. Numbers used for computing difference, * hence this works when difference below 2**21 = 34 years */ boxint s1 = (boxint)DT_DAY (dt1) * 24 * 60 * 60 + DT_HOUR (dt1) * 60 * 60 + DT_MINUTE (dt1) * 60 + DT_SECOND (dt1); boxint s2 = (boxint)DT_DAY (dt2) * 24 * 60 * 60 + DT_HOUR (dt2) * 60 * 60 + DT_MINUTE (dt2) * 60 + DT_SECOND (dt2); char *unit = interval_odbc_to_text (long_unit, "timestampdiff"); if (0 == stricmp (unit, "day")) return box_num ((boxint)DT_DAY (dt2) - (boxint)DT_DAY (dt1)); if (0 == stricmp (unit, "hour")) return box_num ((s2 - s1) / (60 * 60)); if (0 == stricmp (unit, "minute")) return box_num ((s2 - s1) / 60); if (0 == stricmp (unit, "second")) return box_num (s2 - s1); dt_to_GMTimestamp_struct (dt2, &ts2); dt_to_GMTimestamp_struct (dt1, &ts1); if (0 == stricmp (unit, "month")) return box_num ((boxint)(ts2.year * 12 + ts2.month) - (boxint)(ts1.year * 12 + ts1.month)); if (0 == stricmp (unit, "year")) return box_num ((boxint)ts2.year - (boxint)ts1.year); sqlr_new_error ("22015", "DT004", "Bad interval in timestampdiff: %s.", unit); return NULL; }
static caddr_t sa_to_dk (MonoArray *mono_list, int ofs, int mode, void *udt) { guint32 ret_type; int clr_object = 0; MonoObject *type, *value; caddr_t ret = NULL; MonoClass *cls; int len = mono_array_length (mono_list), inx; dk_set_t ret_set = NULL; type = (MonoObject *)mono_array_get (mono_list, gpointer, ofs + 0); ret_type = *(guint32 *)((char *)type + sizeof (MonoObject)); if (!ret_type) { char *error_text; caddr_t err = NULL; value = (MonoObject *)mono_array_get (mono_list, gpointer, ofs + 1); error_text = mono_string_to_utf8 ((MonoString *)value); if (error_text) err = srv_make_new_error ("42000", "MN002", "Mono error : %.200s", mono_class_get_name (mono_object_get_class (value)), error_text); else err = srv_make_new_error ("42000", "MN003", "Unknown mono error"); g_free (error_text); sqlr_resignal (err); } /* get type of object */ clr_object = 0; if (ret_type == 5 || ret_type == 6) clr_object = 1; for (inx = 1; inx < len; inx++) { value = (MonoObject *)mono_array_get (mono_list, gpointer, ofs + inx); if (value) { cls = mono_object_get_class (value); if (cls == mono_get_int32_class ()) { gint32 v = *(gint32 *)((char *)value + sizeof (MonoObject)); if (clr_object) { void * what_udt; if (mode) { /*add_id (v);*/ ret = box_num (v); } else { what_udt = udt_find_class_for_clr_instance (v, udt); if (what_udt) { /*add_id (v);*/ ret = cpp_udt_clr_instance_allocate (v, what_udt); } else { sqlr_new_error ("22023", "MN005", "Can't map Mono result to PL type"); } } } else ret = box_num (v); } else if (cls == mono_get_uint32_class()) ret = box_num (*(guint32 *)((char *)value + sizeof (MonoObject))); else if (cls == mono_get_single_class ()) ret = box_float (*(float *)((char *)value + sizeof (MonoObject))); else if (cls == mono_get_double_class ()) ret = box_double (*(double *)((char *)value + sizeof (MonoObject))); else if (cls == mono_get_boolean_class ()) ret = box_num (*(guint8 *)((guint8 *)value + sizeof (MonoObject))); else if (cls == mono_get_string_class ()) { char *utf8 = mono_string_to_utf8 ((MonoString *)value); ret = box_utf8_as_wide_char (utf8, NULL, strlen (utf8), 0, DV_WIDE); g_free (utf8); } else { const char *name = mono_class_get_name (cls); sqlr_new_error ("22023", "MN006", "Can't map CLR result of type (%s) to PL type", name ? name : "<unknown>"); } } else ret = NULL; if (ret_type != 3 && ret_type != 4 && ret_type != 5) return ret; else dk_set_push (&ret_set, ret); } return list_to_array (dk_set_nreverse (ret_set)); }
caddr_t bif_im_get_impl (caddr_t * qst, caddr_t * err, state_slot_t ** args, int is_file_in, int op, const char *bifname) { im_env_t env; char *strg_value = NULL; unsigned long ul_value = 0; caddr_t res = NULL; int is_string_res = (('A' == op) || ('F' == op) || ('I' == op)); int is_list_res = ('2' == op); int is_key_needed = ('A' == op); caddr_t key = is_key_needed ? bif_string_arg (qst, args, (is_file_in ? 1 : 2), bifname) : NULL; im_init (&env, qst, args, bifname); if (is_file_in) im_env_set_filenames (&env, 0, -1); else { im_env_set_input_blob (&env, 0); im_env_set_blob_ext (&env, (is_key_needed ? 3 : 2), -1); } im_read (&env); MagickResetIterator(env.ime_magick_wand); while (MagickNextImage (env.ime_magick_wand) != MagickFalse) { switch (op) { case 'A': strg_value = MagickGetImageAttribute (env.ime_magick_wand, key); break; case 'F': strg_value = MagickGetImageFormat (env.ime_magick_wand); break; case 'I': strg_value = MagickIdentifyImage (env.ime_magick_wand); break; case 'W': ul_value = MagickGetImageWidth (env.ime_magick_wand); break; case 'H': ul_value = MagickGetImageHeight (env.ime_magick_wand); break; case 'D': ul_value = MagickGetImageDepth (env.ime_magick_wand); break; case '2': ul_value = MagickGetImageWidth (env.ime_magick_wand); if (ul_value) { dk_free_tree (res); res = dk_alloc_box (2 * sizeof (caddr_t), DV_ARRAY_OF_POINTER); ((caddr_t *)res)[0] = box_num (ul_value); ((caddr_t *)res)[1] = box_num (MagickGetImageHeight (env.ime_magick_wand)); } break; } } if (is_string_res) { if (strg_value) { res = box_dv_short_string (strg_value); MagickRelinquishMemory (strg_value); } } else if (!is_list_res) { if (ul_value) res = box_num (ul_value); } if (NULL == res) res = NEW_DB_NULL; im_leave (&env); return res; }
caddr_t bif_timezone (caddr_t * qst, caddr_t * err_ret, state_slot_t ** args) { caddr_t arg = bif_date_arg (qst, args, 0, "timezone"); return box_num (DT_TZ (arg)); }
/* equal to ARTM_BIN_FUNC (box_mod, %, numeric_modulo, 1) with some extensions */ caddr_t box_mod (ccaddr_t box1, ccaddr_t box2, caddr_t * qst, state_slot_t * target) { NUMERIC_VAR (dn1); NUMERIC_VAR (dn2); dtp_t dtp1, dtp2, res_dtp; retry_rdf_boxes: NUM_TO_MEM (dn1, dtp1, box1); NUM_TO_MEM (dn2, dtp2, box2); if (dtp1 == DV_DB_NULL || dtp2 == DV_DB_NULL) goto null_result; \ if (n_coerce ((caddr_t) & dn1, (caddr_t) & dn2, dtp1, dtp2, &res_dtp)) { switch (res_dtp) { case DV_LONG_INT: if (0 == *(boxint *) &dn2) sqlr_new_error ("22012", "SR088", "Division by 0."); if (target) return (qst_set_long (qst, target, (*(boxint *) &dn1 % * (boxint *) &dn2)), (caddr_t) 0); return (box_num (*(boxint *) &dn1 % * (boxint *) &dn2)); case DV_SINGLE_FLOAT: if (0 == *(float *) &dn2) sqlr_new_error ("22012", "SR089", "Division by 0."); if (target) return (qst_set_float (qst, target, (float) fmod (*(float *) &dn1, * (float *) &dn2)), (caddr_t) 0); return (box_float ((float) fmod (*(float *) &dn1, * (float *) &dn2))); case DV_DOUBLE_FLOAT: if (0 == *(double*) &dn2) sqlr_new_error ("22012", "SR090", "Division by 0."); if (target) return (qst_set_double (qst, target, fmod (*(double*) &dn1, *(double*) &dn2)), (caddr_t) 0); return (box_double (fmod (*(double*) &dn1, *(double*) &dn2))); case DV_NUMERIC: return (numeric_bin_op (numeric_modulo, (numeric_t) &dn1, (numeric_t) &dn2, qst, target)); } } else { if (dtp1 == DV_RDF || dtp2 == DV_RDF) { if (dtp1 == DV_RDF) box1 = ((rdf_box_t *)(box1))->rb_box; if (dtp2 == DV_RDF) box2 = ((rdf_box_t *)(box2))->rb_box; goto retry_rdf_boxes; } if (((query_instance_t *)qst)->qi_query->qr_no_cast_error) goto null_result; /* see below */ sqlr_new_error ("22003", "SR087", "Non numeric arguments to arithmetic operation modulo"); } null_result: \ if (target) \ { \ qst_set_bin_string (qst, target, NULL, 0, DV_DB_NULL); \ return NULL; \ } \ return (dk_alloc_box (0, DV_DB_NULL)); \ }