static void moreswitches(const char *s, struct cmdline_options *opt, int envopt) { int argc, i; char **argv, *p; const char *ap = 0; VALUE argstr, argary; while (ISSPACE(*s)) s++; if (!*s) return; argstr = rb_str_tmp_new(strlen(s) + 2); argary = rb_str_tmp_new(0); p = RSTRING_PTR(argstr); *p++ = ' '; strcpy(p, s); ap = 0; rb_str_cat(argary, (char *)&ap, sizeof(ap)); while (*p) { ap = p; rb_str_cat(argary, (char *)&ap, sizeof(ap)); while (*p && !ISSPACE(*p)) ++p; if (!*p) break; *p++ = '\0'; while (ISSPACE(*p)) ++p; } argc = RSTRING_LEN(argary) / sizeof(ap); ap = 0; rb_str_cat(argary, (char *)&ap, sizeof(ap)); argv = (char **)RSTRING_PTR(argary); while ((i = proc_options(argc, argv, opt, envopt)) > 1 && (argc -= i) > 0) { argv += i; if (**argv != '-') { *--*argv = '-'; } if ((*argv)[1]) { ++argc; --argv; } } /* get rid of GC */ rb_str_resize(argary, 0); rb_str_resize(argstr, 0); }
static VALUE imf_jpeg_src_mgr_new(VALUE image_source) { imf_jpeg_src_mgr_t *srcmgr; VALUE obj = TypedData_Make_Struct( cSourceManager, imf_jpeg_src_mgr_t, &imf_jpeg_src_mgr_data_type, srcmgr); srcmgr->image_source = image_source; srcmgr->buffer = rb_str_tmp_new(IMF_JPEG_BUFFER_SIZE); srcmgr->pub.init_source = imf_jpeg_src_mgr_init_source; srcmgr->pub.fill_input_buffer = imf_jpeg_src_mgr_fill_input_buffer; srcmgr->pub.skip_input_data = imf_jpeg_src_mgr_skip_input_data; srcmgr->pub.resync_to_restart = jpeg_resync_to_restart; /* use default method */ srcmgr->pub.term_source = imf_jpeg_src_mgr_term_source; srcmgr->pub.bytes_in_buffer = 0; srcmgr->pub.next_input_byte = NULL; return obj; }
static boolean imf_jpeg_src_mgr_fill_input_buffer(j_decompress_ptr cinfo) { imf_jpeg_src_mgr_t *srcmgr = IMF_JPEG_SRC_MGR(cinfo->src); srcmgr->buffer = rb_funcall(srcmgr->image_source, id_read, 1, INT2FIX(IMF_JPEG_BUFFER_SIZE)); if (NIL_P(srcmgr->buffer)) srcmgr->buffer = rb_str_tmp_new(2); if (NIL_P(srcmgr->buffer) || RSTRING_LEN(srcmgr->buffer) == 0) { if (srcmgr->start_of_source) ERREXIT(cinfo, JERR_INPUT_EMPTY); WARNMS(cinfo, JWRN_JPEG_EOF); /* Insert a face EOI marker */ rb_str_resize(srcmgr->buffer, 2); RSTRING_PTR(srcmgr)[0] = '\xFF'; RSTRING_PTR(srcmgr)[1] = JPEG_EOI; } srcmgr->pub.next_input_byte = (JOCTET const *) RSTRING_PTR(srcmgr->buffer); srcmgr->pub.bytes_in_buffer = RSTRING_LEN(srcmgr->buffer); srcmgr->start_of_source = false; return TRUE; }
static int rb_feature_p(const char *feature, const char *ext, int rb, int expanded, const char **fn) { VALUE features, this_feature_index = Qnil, v, p, load_path = 0; const char *f, *e; long i, len, elen, n; st_table *loading_tbl, *features_index; st_data_t data; int type; if (fn) *fn = 0; if (ext) { elen = strlen(ext); len = strlen(feature) - elen; type = rb ? 'r' : 's'; } else { len = strlen(feature); elen = 0; type = 0; } features = get_loaded_features(); features_index = get_loaded_features_index(); st_lookup(features_index, (st_data_t)feature, (st_data_t *)&this_feature_index); /* We search `features` for an entry such that either "#{features[i]}" == "#{load_path[j]}/#{feature}#{e}" for some j, or "#{features[i]}" == "#{feature}#{e}" Here `e` is an "allowed" extension -- either empty or one of the extensions accepted by IS_RBEXT, IS_SOEXT, or IS_DLEXT. Further, if `ext && rb` then `IS_RBEXT(e)`, and if `ext && !rb` then `IS_SOEXT(e) || IS_DLEXT(e)`. If `expanded`, then only the latter form (without load_path[j]) is accepted. Otherwise either form is accepted, *unless* `ext` is false and an otherwise-matching entry of the first form is preceded by an entry of the form "#{features[i2]}" == "#{load_path[j2]}/#{feature}#{e2}" where `e2` matches %r{^\.[^./]*$} but is not an allowed extension. After a "distractor" entry of this form, only entries of the form "#{feature}#{e}" are accepted. In `rb_provide_feature()` and `get_loaded_features_index()` we maintain an invariant that the array `this_feature_index` will point to every entry in `features` which has the form "#{prefix}#{feature}#{e}" where `e` is empty or matches %r{^\.[^./]*$}, and `prefix` is empty or ends in '/'. This includes both match forms above, as well as any distractors, so we may ignore all other entries in `features`. */ if (!NIL_P(this_feature_index)) { for (i = 0; ; i++) { VALUE entry; long index; if (RB_TYPE_P(this_feature_index, T_ARRAY)) { if (i >= RARRAY_LEN(this_feature_index)) break; entry = RARRAY_AREF(this_feature_index, i); } else { if (i > 0) break; entry = this_feature_index; } index = FIX2LONG(entry); v = RARRAY_AREF(features, index); f = StringValuePtr(v); if ((n = RSTRING_LEN(v)) < len) continue; if (strncmp(f, feature, len) != 0) { if (expanded) continue; if (!load_path) load_path = rb_get_expanded_load_path(); if (!(p = loaded_feature_path(f, n, feature, len, type, load_path))) continue; expanded = 1; f += RSTRING_LEN(p) + 1; } if (!*(e = f + len)) { if (ext) continue; return 'u'; } if (*e != '.') continue; if ((!rb || !ext) && (IS_SOEXT(e) || IS_DLEXT(e))) { return 's'; } if ((rb || !ext) && (IS_RBEXT(e))) { return 'r'; } } } loading_tbl = get_loading_table(); f = 0; if (!expanded) { struct loaded_feature_searching fs; fs.name = feature; fs.len = len; fs.type = type; fs.load_path = load_path ? load_path : rb_get_expanded_load_path(); fs.result = 0; st_foreach(loading_tbl, loaded_feature_path_i, (st_data_t)&fs); if ((f = fs.result) != 0) { if (fn) *fn = f; goto loading; } } if (st_get_key(loading_tbl, (st_data_t)feature, &data)) { if (fn) *fn = (const char*)data; loading: if (!ext) return 'u'; return !IS_RBEXT(ext) ? 's' : 'r'; } else { VALUE bufstr; char *buf; static const char so_ext[][4] = { ".so", ".o", }; if (ext && *ext) return 0; bufstr = rb_str_tmp_new(len + DLEXT_MAXLEN); buf = RSTRING_PTR(bufstr); MEMCPY(buf, feature, char, len); for (i = 0; (e = loadable_ext[i]) != 0; i++) { strlcpy(buf + len, e, DLEXT_MAXLEN + 1); if (st_get_key(loading_tbl, (st_data_t)buf, &data)) { rb_str_resize(bufstr, 0); if (fn) *fn = (const char*)data; return i ? 's' : 'r'; } } for (i = 0; i < numberof(so_ext); i++) { strlcpy(buf + len, so_ext[i], DLEXT_MAXLEN + 1); if (st_get_key(loading_tbl, (st_data_t)buf, &data)) { rb_str_resize(bufstr, 0); if (fn) *fn = (const char*)data; return 's'; } } rb_str_resize(bufstr, 0); } return 0; }
static int rb_feature_p(const char *feature, const char *ext, int rb, int expanded, const char **fn) { VALUE v, features, p, load_path = 0; const char *f, *e; long i, len, elen, n; st_table *loading_tbl; st_data_t data; int type; if (fn) *fn = 0; if (ext) { elen = strlen(ext); len = strlen(feature) - elen; type = rb ? 'r' : 's'; } else { len = strlen(feature); elen = 0; type = 0; } features = get_loaded_features(); for (i = 0; i < RARRAY_LEN(features); ++i) { v = RARRAY_PTR(features)[i]; f = StringValuePtr(v); if ((n = RSTRING_LEN(v)) < len) continue; if (strncmp(f, feature, len) != 0) { if (expanded) continue; if (!load_path) load_path = rb_get_expanded_load_path(); if (!(p = loaded_feature_path(f, n, feature, len, type, load_path))) continue; expanded = 1; f += RSTRING_LEN(p) + 1; } if (!*(e = f + len)) { if (ext) continue; return 'u'; } if (*e != '.') continue; if ((!rb || !ext) && (IS_SOEXT(e) || IS_DLEXT(e))) { return 's'; } if ((rb || !ext) && (IS_RBEXT(e))) { return 'r'; } } loading_tbl = get_loading_table(); if (loading_tbl) { f = 0; if (!expanded) { struct loaded_feature_searching fs; fs.name = feature; fs.len = len; fs.type = type; fs.load_path = load_path ? load_path : rb_get_load_path(); fs.result = 0; st_foreach(loading_tbl, loaded_feature_path_i, (st_data_t)&fs); if ((f = fs.result) != 0) { if (fn) *fn = f; goto loading; } } if (st_get_key(loading_tbl, (st_data_t)feature, &data)) { if (fn) *fn = (const char*)data; loading: if (!ext) return 'u'; return !IS_RBEXT(ext) ? 's' : 'r'; } else { VALUE bufstr; char *buf; if (ext && *ext) return 0; bufstr = rb_str_tmp_new(len + DLEXT_MAXLEN); buf = RSTRING_PTR(bufstr); MEMCPY(buf, feature, char, len); for (i = 0; (e = loadable_ext[i]) != 0; i++) { strlcpy(buf + len, e, DLEXT_MAXLEN + 1); if (st_get_key(loading_tbl, (st_data_t)buf, &data)) { rb_str_resize(bufstr, 0); if (fn) *fn = (const char*)data; return i ? 's' : 'r'; } } rb_str_resize(bufstr, 0); } } return 0; }
static void load_jpeg(imf_file_format_t *base_fmt, imf_image_t *img, VALUE image_source) { imf_jpeg_format_t *fmt = (imf_jpeg_format_t *) base_fmt; struct jpeg_decompress_struct *cinfo; struct jpeg_error_mgr jerr; JOCTET *buffer_ptr; assert(img != NULL); if (!rb_obj_is_kind_of(image_source, imf_cIMF_ImageSource)) { rb_raise(rb_eTypeError, "image_source must be an IMF::ImageSource object"); } cinfo = &fmt->cinfo; cinfo->err = jpeg_std_error(&jerr); cinfo->err->error_exit = jpeg_error_exit; jpeg_create_decompress(cinfo); fmt->running = 1; /* setup source manager */ fmt->srcmgr = init_source_manager(cinfo, image_source); jpeg_read_header(cinfo, TRUE); jpeg_start_decompress(cinfo); /* allocate image buffer */ img->color_space = IMF_COLOR_SPACE_RGB; IMF_IMAGE_UNSET_ALPHA(img); img->component_size = sizeof(JSAMPLE); img->pixel_channels = cinfo->output_components; img->width = cinfo->output_width; img->height = cinfo->output_height; imf_image_allocate_image_buffer(img); /* allocate temporary scanline buffer */ fmt->buffer = rb_str_tmp_new(sizeof(JSAMPLE) * cinfo->output_width * cinfo->output_components); buffer_ptr = (JOCTET *) RSTRING_PTR(fmt->buffer); size_t const pixel_size = img->pixel_channels * img->component_size; size_t const row_size = pixel_size * img->width; uint8_t *row_base_ptr = img->data; size_t y = 0; while (cinfo->output_scanline < cinfo->output_height) { jpeg_read_scanlines(cinfo, &buffer_ptr, 1); memcpy(row_base_ptr, buffer_ptr, row_size); row_base_ptr += img->row_stride; ++y; } /* release temporary buffer memory */ buffer_ptr = NULL; rb_str_resize(fmt->buffer, 0L); jpeg_finish_decompress(cinfo); jpeg_destroy_decompress(cinfo); fmt->running = 0; }
static int str_transcode(int argc, VALUE *argv, VALUE *self) { VALUE dest; VALUE str = *self; long blen, slen; unsigned char *buf, *bp, *sp, *fromp; rb_encoding *from_enc, *to_enc; const char *from_e, *to_e; int from_encidx, to_encidx; VALUE from_encval, to_encval; const rb_transcoder *my_transcoder; rb_transcoding my_transcoding; int final_encoding = 0; VALUE opt; int options = 0; opt = rb_check_convert_type(argv[argc-1], T_HASH, "Hash", "to_hash"); if (!NIL_P(opt)) { VALUE v; argc--; v = rb_hash_aref(opt, sym_invalid); if (NIL_P(v)) { rb_raise(rb_eArgError, "unknown value for invalid: setting"); } else if (v==sym_ignore) { options |= INVALID_IGNORE; } } if (argc < 1 || argc > 2) { rb_raise(rb_eArgError, "wrong number of arguments (%d for 1..2)", argc); } if ((to_encidx = rb_to_encoding_index(to_encval = argv[0])) < 0) { to_enc = 0; to_encidx = 0; to_e = StringValueCStr(to_encval); } else { to_enc = rb_enc_from_index(to_encidx); to_e = rb_enc_name(to_enc); } if (argc==1) { from_encidx = rb_enc_get_index(str); from_enc = rb_enc_from_index(from_encidx); from_e = rb_enc_name(from_enc); } else if ((from_encidx = rb_to_encoding_index(from_encval = argv[1])) < 0) { from_enc = 0; from_e = StringValueCStr(from_encval); } else { from_enc = rb_enc_from_index(from_encidx); from_e = rb_enc_name(from_enc); } if (from_enc && from_enc == to_enc) { return -1; } if (from_enc && to_enc && rb_enc_asciicompat(from_enc) && rb_enc_asciicompat(to_enc)) { if (ENC_CODERANGE(str) == ENC_CODERANGE_7BIT) { return to_encidx; } } if (encoding_equal(from_e, to_e)) { return -1; } do { /* loop for multistep transcoding */ /* later, maybe use smaller intermediate strings for very long strings */ if (!(my_transcoder = transcode_dispatch(from_e, to_e))) { rb_raise(rb_eArgError, "transcoding not supported (from %s to %s)", from_e, to_e); } my_transcoding.transcoder = my_transcoder; if (my_transcoder->preprocessor) { fromp = sp = (unsigned char *)RSTRING_PTR(str); slen = RSTRING_LEN(str); blen = slen + 30; /* len + margin */ dest = rb_str_tmp_new(blen); bp = (unsigned char *)RSTRING_PTR(dest); my_transcoding.ruby_string_dest = dest; (*my_transcoder->preprocessor)(&fromp, &bp, (sp+slen), (bp+blen), &my_transcoding); if (fromp != sp+slen) { rb_raise(rb_eArgError, "not fully converted, %td bytes left", sp+slen-fromp); } buf = (unsigned char *)RSTRING_PTR(dest); *bp = '\0'; rb_str_set_len(dest, bp - buf); str = dest; } fromp = sp = (unsigned char *)RSTRING_PTR(str); slen = RSTRING_LEN(str); blen = slen + 30; /* len + margin */ dest = rb_str_tmp_new(blen); bp = (unsigned char *)RSTRING_PTR(dest); my_transcoding.ruby_string_dest = dest; my_transcoding.flush_func = str_transcoding_resize; transcode_loop(&fromp, &bp, (sp+slen), (bp+blen), my_transcoder, &my_transcoding, options); if (fromp != sp+slen) { rb_raise(rb_eArgError, "not fully converted, %td bytes left", sp+slen-fromp); } buf = (unsigned char *)RSTRING_PTR(dest); *bp = '\0'; rb_str_set_len(dest, bp - buf); if (my_transcoder->postprocessor) { str = dest; fromp = sp = (unsigned char *)RSTRING_PTR(str); slen = RSTRING_LEN(str); blen = slen + 30; /* len + margin */ dest = rb_str_tmp_new(blen); bp = (unsigned char *)RSTRING_PTR(dest); my_transcoding.ruby_string_dest = dest; (*my_transcoder->postprocessor)(&fromp, &bp, (sp+slen), (bp+blen), &my_transcoding); if (fromp != sp+slen) { rb_raise(rb_eArgError, "not fully converted, %td bytes left", sp+slen-fromp); } buf = (unsigned char *)RSTRING_PTR(dest); *bp = '\0'; rb_str_set_len(dest, bp - buf); } if (encoding_equal(my_transcoder->to_encoding, to_e)) { final_encoding = 1; } else { from_e = my_transcoder->to_encoding; str = dest; } } while (!final_encoding); /* set encoding */ if (!to_enc) { to_encidx = rb_define_dummy_encoding(to_e); } *self = dest; return to_encidx; }
void ruby_init_loadpath_safe(int safe_level) { VALUE load_path; extern const char ruby_initial_load_paths[]; const char *paths = ruby_initial_load_paths; #if defined LOAD_RELATIVE # if defined HAVE_DLADDR || (defined __CYGWIN__ && defined CCP_WIN_A_TO_POSIX) # define VARIABLE_LIBPATH 1 # else # define VARIABLE_LIBPATH 0 # endif # if VARIABLE_LIBPATH char *libpath; VALUE sopath; # else char libpath[MAXPATHLEN + 1]; size_t baselen; # endif char *p; #if defined _WIN32 || defined __CYGWIN__ # if VARIABLE_LIBPATH sopath = rb_str_tmp_new(MAXPATHLEN); libpath = RSTRING_PTR(sopath); GetModuleFileName(libruby, libpath, MAXPATHLEN); # else GetModuleFileName(libruby, libpath, sizeof libpath); # endif #elif defined(__EMX__) _execname(libpath, sizeof(libpath) - 1); #elif defined(HAVE_DLADDR) Dl_info dli; if (dladdr(expand_include_path, &dli)) { VALUE fname = rb_str_new_cstr(dli.dli_fname); sopath = rb_file_absolute_path(fname, Qnil); rb_str_resize(fname, 0); } else { sopath = rb_str_new(0, 0); } libpath = RSTRING_PTR(sopath); #endif #if !VARIABLE_LIBPATH libpath[sizeof(libpath) - 1] = '\0'; #endif #if defined DOSISH translit_char(libpath, '\\', '/'); #elif defined __CYGWIN__ { # if VARIABLE_LIBPATH const int win_to_posix = CCP_WIN_A_TO_POSIX | CCP_RELATIVE; size_t newsize = cygwin_conv_path(win_to_posix, libpath, 0, 0); if (newsize > 0) { VALUE rubylib = rb_str_tmp_new(newsize); p = RSTRING_PTR(rubylib); if (cygwin_conv_path(win_to_posix, libpath, p, newsize) == 0) { rb_str_resize(sopath, 0); sopath = rubylib; libpath = p; } } # else char rubylib[FILENAME_MAX]; cygwin_conv_to_posix_path(libpath, rubylib); strncpy(libpath, rubylib, sizeof(libpath)); # endif } #endif p = strrchr(libpath, '/'); if (p) { *p = 0; if (p - libpath > 3 && !(STRCASECMP(p - 4, "/bin") && strcmp(p - 4, "/lib"))) { p -= 4; *p = 0; } } #if !VARIABLE_LIBPATH else { strlcpy(libpath, ".", sizeof(libpath)); p = libpath + 1; } baselen = p - libpath; #define BASEPATH() rb_str_buf_cat(rb_str_buf_new(baselen+len), libpath, baselen) #else rb_str_set_len(sopath, p - libpath); #define BASEPATH() rb_str_dup(sopath) #endif #define RUBY_RELATIVE(path, len) rb_str_buf_cat(BASEPATH(), path, len) #else #define RUBY_RELATIVE(path, len) rubylib_mangled_path(path, len) #endif #define incpush(path) rb_ary_push(load_path, (path)) load_path = GET_VM()->load_path; if (safe_level == 0) { ruby_push_include(getenv("RUBYLIB"), identical_path); } while (*paths) { size_t len = strlen(paths); incpush(RUBY_RELATIVE(paths, len)); paths += len + 1; } }