diff options
author | axel <axel@liljencrantz.se> | 2006-06-04 19:35:32 +1000 |
---|---|---|
committer | axel <axel@liljencrantz.se> | 2006-06-04 19:35:32 +1000 |
commit | e7e3e8ee74206cd693ab57933251d4381090b20e (patch) | |
tree | 2d0fc8cb63a18d062f2411528e2ac9ed7597f414 /builtin_set.c | |
parent | 6fd69bdda8b4d185fb636047ab8914989fc66252 (diff) |
Add support for negative indices in arrays. Negative indices count from the end of an array, so -4 is the fourth index from the end
darcs-hash:20060604093532-ac50b-6e22b2f2ccfe94375fe4c32e41ccec08ca501744.gz
Diffstat (limited to 'builtin_set.c')
-rw-r--r-- | builtin_set.c | 27 |
1 files changed, 18 insertions, 9 deletions
diff --git a/builtin_set.c b/builtin_set.c index 3db78504..0b888f08 100644 --- a/builtin_set.c +++ b/builtin_set.c @@ -177,7 +177,8 @@ static int my_env_set( const wchar_t *key, array_list_t *val, int scope ) */ static int parse_index( array_list_t *indexes, const wchar_t *src, - const wchar_t *name ) + const wchar_t *name, + int var_count ) { int len; @@ -224,13 +225,20 @@ static int parse_index( array_list_t *indexes, { wchar_t *end; long l_ind = wcstol(src, &end, 10); + int *ind; + if (end == src) { sb_printf(sb_err, _(L"%ls: Invalid index starting at '%ls'\n"), L"set", src); return 0; } + + if( l_ind < 0 ) + { + l_ind = var_count+l_ind+1; + } - int *ind = (int *) calloc(1, sizeof(int)); + ind = (int *) calloc(1, sizeof(int)); *ind = (int) l_ind; al_push(indexes, ind); src = end; @@ -643,13 +651,17 @@ int builtin_set( wchar_t **argv ) int idx_count, val_count; array_list_t values; array_list_t indexes; + array_list_t result; al_init(&values); al_init(&indexes); + al_init(&result); + + tokenize_variable_array( env_get(dest), &result ); for( ; woptind<argc; woptind++ ) { - if( !parse_index( &indexes, argv[woptind], dest ) ) + if( !parse_index( &indexes, argv[woptind], dest, al_get_count( &result ) ) ) { builtin_print_help( argv[0], sb_err ); retcode = 1; @@ -682,10 +694,6 @@ int builtin_set( wchar_t **argv ) Slice indexes have been calculated, do the actual work */ - array_list_t result; - al_init(&result); - - tokenize_variable_array( env_get(dest), &result ); if( erase ) { erase_values(&result, &indexes); @@ -712,10 +720,11 @@ int builtin_set( wchar_t **argv ) al_destroy( &value ); } - al_foreach( &result, (void (*)(const void *))&free ); - al_destroy( &result ); } + al_foreach( &result, (void (*)(const void *))&free ); + al_destroy( &result ); + al_foreach( &indexes, (void (*)(const void *))&free ); al_destroy(&indexes); al_destroy(&values); |