0

I found strtok function has some trick during you pass the same string to another function, code as follows:

#include <stdlib.h>
#include <stdio.h>
#include <string.h>

void split_redirect(char input[80], int switch_bit);
void split_background(char *split_cmd);

void split_background(char *split_cmd){

    char *tmp = strchr(split_cmd, '&');
    if (tmp == NULL){ }
    else{
        char *command = strtok(split_cmd,"&");        
        while(command!=NULL){        
            // char *command_next = strtok(NULL,"&");
            printf("command=[%s]\n",command);

            if((strchr(command,'>')!=NULL)||(strchr(command,'<')!=NULL)){ 
                split_redirect(command,0);             
            }
            // command = command_next;
            command = strtok(NULL,"&");
            printf("command_next=[%s]\n",command);     
         }
    }
}

void split_redirect(char input[80], int switch_bit){
     char *tmp ,*tmp2;
     tmp = strchr(input, '>');
     tmp2 = strchr(input, '<');

     if (tmp == NULL && tmp2 == NULL){  }
     else if(tmp2 == NULL && tmp !=NULL){
     // single > 
        char *copy = (char *)malloc(sizeof(input));
        strcpy(copy,input);
        char *tmp = strtok(copy,">");
        char *cmd = tmp;
        tmp = strtok(NULL,"\0");

        if (strchr(tmp,'>')==NULL){
           char *file_name = strtok(tmp," ");
        }
        else{
           free(copy);
           copy=NULL;            
        }
    }
    else{ }
}

void main(int argc,char *argv[]){
    // char *cmd2 = "cmd1 > txt & cmd2 > txt2" // -> each char can't be change, so strotk this string will get seg fault. Modify token to '\0' is illegal. in .RDATA
    char cmd[80] = "cmd1 > txt & cmd2 > txt &"; 
    split_background(cmd);  
}


Expect output:
command=[cmd1 > txt ]
command_next=[ cmd2 > txt ]

The output:
command=[cmd1 > txt ]
command_next=[(null)]

Why when I pass this string to another function will cause the rest of string becomes null string? When I unmark char *command_next = strtok(NULL,"&"); and replace command = strtok(NULL,"&"); to command = command_next; It will print the rest of string as my expectation. Is it relate to how strtok store that string by static memory?

AusCBloke
  • 18,014
  • 6
  • 40
  • 44
James Yang
  • 464
  • 1
  • 5
  • 9
  • I found that topic as my guess.strtok use the same memory location. so the next strtok call in split_redirect function will overwrite the string in same memory location. http://stackoverflow.com/questions/1509654/using-strtok-in-a-loop-in-c – James Yang Nov 10 '11 at 19:29

1 Answers1

2

Read the manual: The strtok function changes the original string and overwrites the delimiter characters with null bytes. The rest of the string doesn't "become null string", but you have to resume the rest of the string one after the last found token.

It's probably best to use strtok idiomatically to extract all tokens, and then process those tokens individually.

Kerrek SB
  • 464,522
  • 92
  • 875
  • 1,084
  • "It's probably best to use strtok idiomatically to extract all tokens, and then process those tokens individually." -> Sure, this is a less risky way to handle this but a little more memory usage. – James Yang Nov 10 '11 at 19:34
  • @Akaing: only if you *copy* the token. You're free to inspect it and decide to ignore it. In any case, unless string processing is your core program activity, this is perhaps not the greatest worry. – Kerrek SB Nov 10 '11 at 19:39