Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people, just like you, are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions

argv substr() question

Posted on 2003-10-30
Last Modified: 2012-08-14
Hello all,
I am mostly a c++ programmer, now programming UPC on a cray so please bare with me.
I am trying to parse a string from argv and am having a few troubles.
ex: entering the following "./CraPov -[option] povrayfile.pov"
I would like to parse argv to return [povrayfile] (without the ".pov" extention)

I was wondering if there is a simple function to do this for me or if i have to use substr() and write my own. Thankz for your help in advance.

Simplified version of code is as follows:

int main(int argc, char **argv) {
      int pf;
      char povf[32];

      pf = argc - 1;
        // Code to parse string

Question by:loki982
  • 2
  • 2
  • 2
  • +3

Expert Comment

ID: 9655597
refer to the function  strtok
dat wud help u

Expert Comment

ID: 9655619
LVL 10

Expert Comment

ID: 9655643
I guess u can use strtok

char *str ;
str = strtok ( povf, "." ) ;
Ransomware-A Revenue Bonanza for Service Providers

Ransomware – malware that gets on your customers’ computers, encrypts their data, and extorts a hefty ransom for the decryption keys – is a surging new threat.  The purpose of this eBook is to educate the reader about ransomware attacks.


Expert Comment

ID: 9655918
//suppose  you have argv[1] ="abc.prov"
// then use following code

char buf[32],*tmp;

tmp = buf;

while( *tmp !='.') tmp++;
// you have found a '.' so terminate the string by making this character as \0 or null

if(*tmp == '.') *tmp ='\0';

// this makes buffer to be  "abc"
LVL 23

Expert Comment

ID: 9656075
All previous solutions will fail on "./povrayfile.pov", "./povrayfile", or "abc.tar.gz"

#include <string.h>
#include <libgen.h>

/* check for '.' in just the basename first so you don't trip on "./filename"  
 * use rindex so you strip off only the last extension

if (rindex(basename(arg), '.'))
     * rindex(arg, '.') = '\0';

LVL 45

Expert Comment

by:Kent Olsen
ID: 9657694

Hi loki982,

Lot's of suggestions here.  All seem to trip on the issue of embedded periods.  It would seem that the key item isn't just the period, but the slash.  As several posts have pointed out, the file name could also be a path.

int main (int argc, char *argv)
  char *FileName;

  FileName = GetFileName (arvg[argc-1]);  /* Sanity check required for parameter count!  */

  fprintf (stdout, "File name is '%s'\n", FileName);

  Return the file name portion of a path
  If the file name contains an extension, drop the extension

char *GetFileName (char *FileName)
  char *cc, *oc;
  char *tfn;
  char *Fn = strdup (FileName);  /* Make our own string so as to not change the original!  */

/*  Look for the LAST '/' delimeter  */

  occ = FileName;
  while (cc = strchr (occ, '/'))
    occ = cc;

  tfn = occ;  /*  tfn points to the filename portion of the path*/

/*  Now look for the LAST '.' in the file name */

  while (cc = strchr (occ, '.'))
    occ = cc;

  if (*occ == '.')  /*  The file name contained at least one period so we'll end the string at the last one */
    *occ = 0;

  tfn = strdup (occ);  /*  Make a string that is the desired filename  */
  free (Fn);              /*  Free the scratch buffer that contained the original path  */
  return (tfn);

Let me caution that this is dangerous.  Instead of arbitrarily dropping the extension, the function should check that the extension is an allowed type.  If so, it can then drop the extension, if not the function should probably return NULL so that the calling function can inform the user that an an invalid file was entered.  To make this happen, replace:

  if (*occ == '.')
    *occ = 0;


  if (*occ == '.')  /*  The file name included an extension  */
    if (strcmp (occ+1, "pov") == 0)  /*  Valid extension  */
      *occ = 0;
      free (Fn);
      return (NULL);

Cray programmer huh?  I'm and old CDCer with experience on everything that they made after the 3000 series.  Another common poster here is grg99 who goes back to CDC's 160A days!  How about sending me a note offline -- my e-mail address is in my profile.


Author Comment

ID: 9666911
sorry it took so long to respond(halloween &all)
overall this seems to work quite well...
though the options are still giving me bit of a headache

i am trying to get the arguments before the povfile
i have a working version within main but i'm trying
like hell to get it into a function with no luck
i just don't know how to increment PovOp correctly
any help would be greatly appreciated

when executed:

$ ./a.out -foo -bar hello.pov
File name is 'hello'
Povray Options are '-foo -bar '
Povray Options are '-foo'

Code is as follows:

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

char *GetFileName(char * FileName);
char *GetOptions(char * PovOp, int OpLen);

int main(int argc, char **argv) {
      char *FileName,*FN;
      char *Options;
      char OP[256][256];
      char PovOp[256];
      int i,pop;

      FileName = GetFileName(argv[argc-1]);

      // options works in main...
      if(argc>2) {
            strcat(PovOp," ");
            if(argc>3) {
                  for(i=2;i<argc-1;i++) {
                        strcat(PovOp," ");
      else {

      Options = GetOptions(argv[1],argc-1);

      fprintf(stdout,"File name is '%s'\n",FileName);
      fprintf(stdout,"Povray Options are '%s'\n",Options);      
      fprintf(stdout,"Povray Options are '%s'\n",PovOp);

char * GetOptions(char *PovOp, int OpLen)
      int pl,i;
      char PO[256];
      char *pf;
      char *poptr;
      char *tfn;
      pl = OpLen;
      if(pl>2) {
            strcat(PO," ");
            if(pl>3) {
                  for(i=2;i<pl-1;i++) {
                        strcat(PO," ");
                        // unshure how to increment PovOp
      else {

char *GetFileName(char *FileName)
      char *a2F, *a2E;
      char *fnptr;
      char *tfn;
      char *Fn = strdup(FileName);
      fnptr = FileName;
      while(a2F = strchr(fnptr,'/')) {
            fnptr = a2F;
      a2E = fnptr;
      while(a2F = strchr(a2E,'.')) {
            a2E = a2F;
      if(*a2E=='.') {
            if(strcmp(a2E+1,"pov")==0) {
                  *a2E = 0;
            else {
                  fprintf(stderr,"Filename Mismatch");
LVL 45

Accepted Solution

Kent Olsen earned 50 total points
ID: 9670500

Hi loki,

I'm unsure of where you're trying to go so I'll venture a guess:

If you want the function to build the options table just as main() does now:

  Just move the code in main() to the function and call it as GetOptions (argc, argv);  Note that main() doesn't really BUILD an options table.  It constructs a string that is the concatenation of all of the options on the command line.  (This is probably not real useful to you.)  The reason that the function seems to be failing is that the function call:

  Options = GetOptions(argv[1],argc-1);

advances to start with the first parameter after the command name by incrementing the index and decrementing the count.  GetOptions() and main() are hard-coded to look for a parameter by position.  Note that main checks by "if (argc > 2)" and "if (argc > 3)".  The functions uses these exact same checks (with variable *pl*).  *pl* is derived from OpLen, which has the value of argc-1 so you seem to miss the last options parameter.

Note also that there's an easier way.

strcpy (PovOP, "");
for (int idx = 1; idx < argc; idx++)
  if (*argv[idx] == '-')
    strcat (PovOP, argv[idx]);
    atrcat (PobOP, " ");

This builds the string from all of the parameters that begin with "-".  Perhaps not what you need, but in some instances this could be exactly what you want.  Consider the command line:

Cmd [<options> Filename1 ...] ...

This expands to something like this:

Cmd -a -s -d -r -t -f F1 F2 F3 -a -q -w -e -r F4 F5 F6 F6 -s -d -f F7 (etc...)

Using the snippet above (with breaks at the file names) you can capture the appropriate flags, process the files associated with those flags and move on.

Very few commands actually use this format, but there are a few.



Author Comment

ID: 9676418
Everything works perfectly!
Thankz for the help all,

Featured Post

How Do You Stack Up Against Your Peers?

With today’s modern enterprise so dependent on digital infrastructures, the impact of major incidents has increased dramatically. Grab the report now to gain insight into how your organization ranks against your peers and learn best-in-class strategies to resolve incidents.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
Convert image to byte array 8 209
chcp 65001 File encoding 66 272
smtp c source code 7 85
windows 10 pro lost profile. 10 43
An Outlet in Cocoa is a persistent reference to a GUI control; it connects a property (a variable) to a control.  For example, it is common to create an Outlet for the text field GUI control and change the text that appears in this field via that Ou…
Preface I don't like visual development tools that are supposed to write a program for me. Even if it is Xcode and I can use Interface Builder. Yes, it is a perfect tool and has helped me a lot, mainly, in the beginning, when my programs were small…
The goal of this video is to provide viewers with basic examples to understand opening and writing to files in the C programming language.
The goal of this video is to provide viewers with basic examples to understand recursion in the C programming language.

856 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question