Sorry, forgot to attach the file.
--
Salu2
Index: src/pdb.c
===================================================================
--- src/pdb.c (revisión: 28197)
+++ src/pdb.c (copia de trabajo)
@@ -219,9 +219,8 @@
Parrot_exception exp;
if (setjmp(exp.destination)) {
- char *msg = string_to_cstring(interp, interp->exceptions->msg);
- fprintf(stderr, "Caught exception: %s\n", msg);
- string_cstring_free(msg);
+ fprintf(stderr, "Caught exception: %s\n",
+ Parrot_string_get_cstring(interp->exceptions->msg));
return;
}
Index: src/oo.c
===================================================================
--- src/oo.c (revisión: 28197)
+++ src/oo.c (copia de trabajo)
@@ -405,7 +405,7 @@
INTVAL
Parrot_get_vtable_index(PARROT_INTERP, ARGIN(const STRING *name))
{
- char * const name_c = string_to_cstring(interp, name);
+ const char * const name_c = Parrot_string_get_cstring(interp, name);
/* some of the first "slots" don't have names. skip 'em. */
INTVAL low = PARROT_VTABLE_LOW;
@@ -419,7 +419,6 @@
const INTVAL cmp = strcmp(name_c, meth_c + 2);
if (cmp == 0) {
- string_cstring_free(name_c);
return mid;
}
else if (cmp > 0)
@@ -428,8 +427,6 @@
high = mid;
}
- string_cstring_free(name_c);
-
return -1;
}
Index: src/hll.c
===================================================================
--- src/hll.c (revisión: 28197)
+++ src/hll.c (copia de trabajo)
@@ -93,7 +93,7 @@
if (entry_name && !STRING_IS_EMPTY(entry_name)) {
STRING *const_name = const_string(interp,
- string_to_cstring(interp, entry_name));
+ Parrot_string_get_cstring(interp, entry_name));
VTABLE_set_pmc_keyed_str(interp, hll_info, const_name, entry);
}
Index: src/ops/core.ops
===================================================================
--- src/ops/core.ops (revisión: 28197)
+++ src/ops/core.ops (copia de trabajo)
@@ -185,12 +185,11 @@
=cut
inline op branch_cs(in STR) :base_loop :check_event :flow {
- char * const label = string_to_cstring(interp, $1);
+ char * const label = string_to_cstring(interp, $1);
PackFile_FixupEntry * const fe =
PackFile_find_fixup_entry(interp, enum_fixup_label, label);
if (!fe) {
- string_cstring_free(label);
real_exception(interp, NULL, 1, "branch_cs: fixup for '%Ss' not found",
$1);
}
@@ -199,7 +198,6 @@
Parrot_switch_to_cs(interp, fe->seg, 1);
}
mem_sys_free(fe);
- string_cstring_free(label);
interp->resume_flag = 2;
goto ADDRESS(0);
}
@@ -1244,7 +1242,7 @@
}
op dlfunc(out PMC, invar PMC, in STR, in STR) {
- char * const name = string_to_cstring(interp, ($3));
+ const char * const name = Parrot_string_get_cstring(interp, ($3));
void *ptr = Parrot_dlsym(
PMC_IS_NULL($2) ? NULL :
VTABLE_defined(interp, $2) ? PMC_data($2) :
@@ -1264,13 +1262,11 @@
VTABLE_set_pointer_keyed_str(interp, $1, $4, F2DPTR(p));
PObj_get_FLAGS($1) |= PObj_private1_FLAG;
}
- string_cstring_free(name);
}
op dlvar(out PMC, invar PMC, in STR) {
- char * const name = string_to_cstring(interp, ($3));
+ const char * const name = Parrot_string_get_cstring(interp, ($3));
void * const p = Parrot_dlsym(PMC_IS_NULL($2) ? NULL : PMC_data($2), name);
- string_cstring_free(name);
if (p == NULL) {
const char * const err = Parrot_dlerror();
Parrot_warn(interp, PARROT_WARNINGS_UNDEF_FLAG,
Index: src/global.c
===================================================================
--- src/global.c (revisión: 28197)
+++ src/global.c (copia de trabajo)
@@ -725,7 +725,6 @@
store_sub_in_multi(PARROT_INTERP, ARGIN(PMC *sub), ARGIN(PMC *ns))
{
INTVAL func_nr;
- char *c_meth;
STRING * const subname = PMC_sub(sub)->name;
PMC *multisub = VTABLE_get_pmc_keyed_str(interp, ns, subname);
@@ -740,11 +739,10 @@
else
VTABLE_push_pmc(interp, multisub, sub);
- c_meth = string_to_cstring(interp, subname);
- func_nr = Parrot_MMD_method_idx(interp, c_meth);
+ func_nr = Parrot_MMD_method_idx(interp,
+ Parrot_string_get_cstring(interp, subname));
if (func_nr >= 0)
Parrot_mmd_rebuild_table(interp, -1, func_nr);
- string_cstring_free(c_meth);
}
/*
Index: src/gc/dod.c
===================================================================
--- src/gc/dod.c (revisión: 28197)
+++ src/gc/dod.c (copia de trabajo)
@@ -625,6 +625,9 @@
}
#endif
+ if (PObj_is_string_TEST(b))
+ Parrot_string_free_cstring(interp, (STRING *) (b));
+
if (PObj_is_shared_TEST(b)) {
/* only mess with shared objects if we
* (and thus everyone) is suspended for
Index: src/string.c
===================================================================
--- src/string.c (revisión: 28197)
+++ src/string.c (copia de trabajo)
@@ -153,6 +153,8 @@
PObj_COW_SET(s);
STRUCT_COPY(d, s);
PObj_sysmem_CLEAR(d);
+ if (! PObj_external_TEST(d))
+ d->cstring_val = NULL;
#if 0
/* XXX FIXME hack to avoid cross-interpreter issue until it
* is fixed correctly. */
@@ -198,6 +200,8 @@
PObj_COW_SET(s);
STRUCT_COPY(d, s);
PObj_sysmem_CLEAR(d);
+ if (! PObj_external_TEST(s))
+ d->cstring_val = NULL;
}
return d;
}
@@ -511,6 +515,7 @@
if (a == NULL || PObj_bufstart(a) == NULL)
return string_copy(interp, b);
+ Parrot_string_free_cstring(interp, a);
saneify_string(a);
saneify_string(b);
@@ -1037,8 +1042,10 @@
dest->bufused = s->bufused * num;
dest->strlen = s->strlen * num;
- if (d != NULL)
+ if (d != NULL) {
+ Parrot_string_free_cstring(interp, * d);
*d = dest;
+ }
return dest;
}
@@ -1166,6 +1173,9 @@
return NULL;
}
+ if (d)
+ Parrot_string_free_cstring(interp, * d);
+
/* abs(-offset) may not be > strlen-1 */
if (offset < 0)
true_offset = (UINTVAL)(src->strlen + offset);
@@ -2061,6 +2071,14 @@
void
string_cstring_free(ARGIN_NULLOK(char *p))
{
+#ifndef NDEBUG
+ {
+ if (p) {
+ int l= strlen(p);
+ memset(p, '!', l);
+ }
+ }
+#endif
mem_sys_free((void *)p);
}
@@ -2637,6 +2655,57 @@
/*
+=item C<const char * Parrot_string_free_cstring>
+
+Free the cached C string created by Parrot_string_get_string,
+called when the Parrot string is deleted or modified.
+
+*/
+
+PARROT_API
+void
+Parrot_string_free_cstring(PARROT_INTERP, ARGIN_NULLOK(const STRING *str))
+{
+ if (str && ! (PObj_external_TEST(str) || PObj_constant_TEST(str))
+ && str->cstring_val) {
+ DECL_CONST_CAST;
+ STRING * strmut = PARROT_const_cast(STRING *, str);
+ string_cstring_free(PARROT_const_cast(char *, strmut->cstring_val));
+ strmut->cstring_val = NULL;
+ }
+}
+
+/*
+
+=item C<const char * Parrot_string_get_cstring>
+
+Convert a Parrot string to a C string. The C string is owned by
+the Parrot string, and is valid until the Parrot string is modified.
+
+=cut
+
+*/
+
+PARROT_API
+const char *
+Parrot_string_get_cstring(PARROT_INTERP, ARGIN_NULLOK(const STRING *str))
+{
+ if (! str)
+ return NULL;
+
+ if (PObj_external_TEST(str) || PObj_constant_TEST(str))
+ return str->strstart;
+
+ if (! str->cstring_val) {
+ DECL_CONST_CAST;
+ STRING * strmut = PARROT_const_cast(STRING *, str);
+ strmut->cstring_val = string_to_cstring(interp, str);
+ }
+ return str->cstring_val;
+}
+
+/*
+
=item C<INTVAL Parrot_string_is_cclass>
Returns 1 if the codepoint of string C<s> at given offset is in the given
Index: src/pmc/os.pmc
===================================================================
--- src/pmc/os.pmc (revisión: 28197)
+++ src/pmc/os.pmc (copia de trabajo)
@@ -109,13 +109,12 @@
METHOD chdir(STRING *path) {
int error;
- char * const cpath = string_to_cstring(interp, path);
+ const char * const cpath = Parrot_string_get_cstring(interp, path);
#ifdef _MSC_VER
error = _chdir(cpath);
#else
error = chdir(cpath);
#endif
- string_cstring_free(cpath);
if (error) {
char *errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
@@ -135,12 +134,11 @@
METHOD rm(STRING *path) {
struct stat info;
- char *cpath = string_to_cstring(interp, path);
+ const char * const cpath = Parrot_string_get_cstring(interp, path);
int error = stat(cpath, &info);
if (error) {
const char * const errmsg = strerror(errno);
- string_cstring_free(cpath);
real_exception(interp, NULL, E_SystemError, errmsg);
}
@@ -150,7 +148,6 @@
#else
error = rmdir(cpath);
#endif
- string_cstring_free(cpath);
if (error) {
const char * const errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
@@ -158,7 +155,6 @@
}
else {
error = remove(cpath);
- string_cstring_free(cpath);
if (error) {
const char * const errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
@@ -178,14 +174,13 @@
METHOD mkdir(STRING *path, INTVAL mode) {
int error;
- char * const cpath = string_to_cstring(interp, path);
+ const char * const cpath = Parrot_string_get_cstring(interp, path);
/* should we validate mode? */
#ifdef WIN32
error = _mkdir(cpath);
#else
error = mkdir(cpath, mode);
#endif
- string_cstring_free(cpath);
if (error) {
const char * const errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
@@ -220,9 +215,8 @@
METHOD stat(STRING *path) {
struct stat info;
- char * const cpath = string_to_cstring(interp, path);
+ const char * const cpath = Parrot_string_get_cstring(interp, path);
const int error = stat(cpath, &info);
- string_cstring_free(cpath);
if (error) {
const char * const errmsg = strerror(errno);
@@ -280,13 +274,12 @@
METHOD lstat(STRING *path) {
struct stat info;
- char * const cpath = string_to_cstring(interp, path);
+ const char * const cpath = Parrot_string_get_cstring(interp, path);
#ifdef WIN32
const int error = stat(cpath, &info);
#else
const int error = lstat(cpath, &info);
#endif
- string_cstring_free(cpath);
if (error) {
const char * const errmsg = strerror(errno);
@@ -327,13 +320,10 @@
METHOD symlink(STRING *from, STRING *to) {
#ifndef WIN32
- char * const cfrom = string_to_cstring(interp, from);
- char * const cto = string_to_cstring(interp, to);
+ const char * const cfrom = Parrot_string_get_cstring(interp, from);
+ const char * const cto = Parrot_string_get_cstring(interp, to);
const int error = symlink(cfrom, cto);
- string_cstring_free(cfrom);
- string_cstring_free(cto);
-
if (error) {
const char * const errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
@@ -356,13 +346,10 @@
METHOD link(STRING *from, STRING *to) {
#ifndef WIN32
- char * const cfrom = string_to_cstring(interp, from);
- char * const cto = string_to_cstring(interp, to);
+ const char * const cfrom = Parrot_string_get_cstring(interp, from);
+ const char * const cto = Parrot_string_get_cstring(interp, to);
const int error = link(cfrom, cto);
- string_cstring_free(cfrom);
- string_cstring_free(cto);
-
if (error) {
const char * const errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
@@ -410,11 +397,9 @@
METHOD chroot(STRING *path) {
#ifndef WIN32
- char * const cpath = string_to_cstring(interp, path);
+ const char * const cpath = Parrot_string_get_cstring(interp, path);
const int error = chroot(cpath);
- string_cstring_free(cpath);
-
if (error) {
const char * const errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
@@ -439,12 +424,10 @@
#ifndef _MSC_VER
struct dirent *dirent;
PMC *array;
- char *cpath = string_to_cstring(interp, path);
+ const char * const cpath = Parrot_string_get_cstring(interp, path);
STRING *retval;
DIR *dir = opendir(cpath);
- string_cstring_free(cpath);
-
if (!dir) {
const char * const errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
@@ -474,13 +457,10 @@
=cut
*/
METHOD rename(STRING *oldpath, STRING *newpath) {
- char * const coldpath = string_to_cstring(interp, oldpath);
- char * const cnewpath = string_to_cstring(interp, newpath);
- const int ret = rename(coldpath, cnewpath);
+ const char * const cfrom = Parrot_string_get_cstring(interp, oldpath);
+ const char * const cto = Parrot_string_get_cstring(interp, newpath);
+ const int ret = rename(cfrom, cto);
- string_cstring_free(coldpath);
- string_cstring_free(cnewpath);
-
if (ret < 0) {
const char * const errmsg = strerror(errno) ;
real_exception(interp, NULL, E_SystemError, "%s", errmsg);
Index: src/pmc/env.pmc
===================================================================
--- src/pmc/env.pmc (revisión: 28197)
+++ src/pmc/env.pmc (copia de trabajo)
@@ -154,14 +154,12 @@
}
}
else {
- char * const keyname = string_to_cstring(interp,
+ const char * const keyname = Parrot_string_get_cstring(interp,
VTABLE_get_string(interp, key));
- char *val = NULL;
if (keyname) {
int free_it = 0;
- val = Parrot_getenv(keyname, &free_it);
- string_cstring_free(keyname);
+ char * val = Parrot_getenv(keyname, &free_it);
if (val) {
STRING *retval = string_from_cstring(interp, val, 0);
@@ -189,17 +187,15 @@
*/
VTABLE PMC *get_pmc_keyed(PMC *key) {
- char * const keyname = string_to_cstring(INTERP,
+ const char * const keyname = Parrot_string_get_cstring(INTERP,
VTABLE_get_string(INTERP, key));
- char *val = NULL;
STRING *retval = NULL;
PMC *return_pmc;
if (keyname) {
int free_it = 0;
- val = Parrot_getenv(keyname, &free_it);
- string_cstring_free(keyname);
+ char * val = Parrot_getenv(keyname, &free_it);
if (val) {
retval = string_from_cstring(INTERP, val, 0);
@@ -228,18 +224,12 @@
*/
VTABLE void set_string_keyed(PMC *key, STRING *value) {
- char * const keyname = string_to_cstring(INTERP,
+ const char * const keyname = Parrot_string_get_cstring(INTERP,
VTABLE_get_string(INTERP, key));
- char * const env_val = string_to_cstring(INTERP, value);
+ const char * const env_val = Parrot_string_get_cstring(INTERP, value);
if (keyname && env_val)
Parrot_setenv(keyname, env_val);
-
- if (keyname)
- string_cstring_free(keyname);
-
- if (env_val)
- string_cstring_free(env_val);
}
/*
Index: src/pmc/file.pmc
===================================================================
--- src/pmc/file.pmc (revisión: 28197)
+++ src/pmc/file.pmc (copia de trabajo)
@@ -66,13 +66,12 @@
METHOD exists(STRING *path) {
struct stat info;
- char *cpath = string_to_cstring(interp, path);
+ const char *cpath = Parrot_string_get_cstring(interp, path);
#ifdef WIN32
int error = stat(cpath, &info);
#else
int error = lstat(cpath, &info);
#endif
- string_cstring_free(cpath);
if (error)
RETURN(INTVAL 0);
@@ -92,13 +91,12 @@
METHOD is_dir(STRING *path) {
struct stat info;
- char *cpath = string_to_cstring(interp, path);
+ const char *cpath = Parrot_string_get_cstring(interp, path);
#ifdef WIN32
int error = stat(cpath, &info);
#else
int error = lstat(cpath, &info);
#endif
- string_cstring_free(cpath);
if (error) {
char *errmsg = strerror(errno);
@@ -123,13 +121,12 @@
METHOD is_file(STRING *path) {
struct stat info;
- char *cpath = string_to_cstring(interp, path);
+ const char *cpath = Parrot_string_get_cstring(interp, path);
#ifdef WIN32
int error = stat(cpath, &info);
#else
int error = lstat(cpath, &info);
#endif
- string_cstring_free(cpath);
if (error) {
char *errmsg = strerror(errno);
@@ -159,11 +156,9 @@
#else
struct stat info;
- char *cpath = string_to_cstring(interp, path);
+ const char *cpath = Parrot_string_get_cstring(interp, path);
int error = lstat(cpath, &info);
- string_cstring_free(cpath);
-
if (error) {
char *errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
@@ -195,17 +190,13 @@
METHOD copy(STRING *from, STRING *to) {
#define CHUNK_SIZE 1024
- char *cfrom = string_to_cstring(interp, from);
+ const char *cfrom = Parrot_string_get_cstring(interp, from);
FILE *source = fopen(cfrom, "rb");
- string_cstring_free(cfrom);
-
if (source) {
- char *cto = string_to_cstring(interp, to);
+ const char *cto = Parrot_string_get_cstring(interp, to);
FILE *target = fopen(cto, "w+b");
- string_cstring_free(cto);
-
if (target) {
char buf[CHUNK_SIZE];
int bytes_read, bytes_written;
@@ -247,13 +238,10 @@
*/
METHOD rename(STRING *from, STRING *to) {
- char *cfrom = string_to_cstring(interp, from);
- char *cto = string_to_cstring(interp, to);
+ const char *cfrom = Parrot_string_get_cstring(interp, from);
+ const char *cto = Parrot_string_get_cstring(interp, to);
int error = rename(cfrom, cto);
- string_cstring_free(cfrom);
- string_cstring_free(cto);
-
if (error) {
char *errmsg = strerror(errno);
real_exception(interp, NULL, E_SystemError, errmsg);
Index: src/datatypes.c
===================================================================
--- src/datatypes.c (revisión: 28197)
+++ src/datatypes.c (copia de trabajo)
@@ -40,18 +40,18 @@
INTVAL
Parrot_get_datatype_enum(PARROT_INTERP, ARGIN(const STRING *type_name))
{
- char * const type = string_to_cstring(interp, type_name);
+ const char * const type = Parrot_string_get_cstring(interp, type_name);
int i;
+ if (! type)
+ return enum_type_undef;
+
for (i = enum_first_type; i < enum_last_type; i++) {
if (strcmp(data_types[i - enum_first_type].name, type) == 0) {
- string_cstring_free(type);
return i;
}
}
- string_cstring_free(type);
-
return enum_type_undef;
}
Index: src/library.c
===================================================================
--- src/library.c (revisión: 28197)
+++ src/library.c (copia de trabajo)
@@ -514,7 +514,7 @@
enum_runtime_ft type)
{
STRING *prefix;
- STRING *full_name;
+ STRING *full_name = 0;
PMC *paths;
INTVAL i, n;
char *prefix_c;
Index: src/io/io_layers.c
===================================================================
--- src/io/io_layers.c (revisión: 28197)
+++ src/io/io_layers.c (copia de trabajo)
@@ -200,11 +200,11 @@
void
PIO_push_layer_str(PARROT_INTERP, ARGIN(PMC *pmc), ARGIN_NULLOK(const STRING *ls))
{
- char * const cls = string_to_cstring(interp, ls);
- ParrotIOLayer * const l = PIO_get_layer(interp, cls);
+ const char * const cls = Parrot_string_get_cstring(interp, ls);
+ ParrotIOLayer * const l = cls ? PIO_get_layer(interp, cls) :
+ (ParrotIOLayer *) NULL;
ParrotIOLayer * newlayer;
- string_cstring_free(cls);
if (!l)
real_exception(interp, NULL, 1, "Layer not found");
Index: include/parrot/string_funcs.h
===================================================================
--- include/parrot/string_funcs.h (revisión: 28197)
+++ include/parrot/string_funcs.h (copia de trabajo)
@@ -53,6 +53,14 @@
FUNC_MODIFIES(*d);
PARROT_API
+void
+Parrot_string_free_cstring(PARROT_INTERP, ARGIN_NULLOK(const STRING *str));
+
+PARROT_API
+const char *
+Parrot_string_get_cstring(PARROT_INTERP, ARGIN_NULLOK(const STRING *str));
+
+PARROT_API
PARROT_PURE_FUNCTION
PARROT_CANNOT_RETURN_NULL
const char * Parrot_string_cstring(SHIM_INTERP, ARGIN(const STRING *str))
Index: include/parrot/pobj.h
===================================================================
--- include/parrot/pobj.h (revisión: 28197)
+++ include/parrot/pobj.h (copia de trabajo)
@@ -121,6 +121,7 @@
UnionVal cache;
Parrot_UInt flags;
char *strstart;
+ const char *cstring_val;
UINTVAL bufused;
UINTVAL strlen;
UINTVAL hashval; /* cached hash value computation */