# Linux Bash Script Question

**URL:** <https://boards.straightdope.com/t/linux-bash-script-question/640712>\
**Category:** Factual Questions\
**Created:** [November 11, 2012, 8:30pm UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712 "2012-11-11T20:30:34Z")\
**Posts on this page:** 11\
**Page:** 2

<div class="post-metadata">

**Author:** ![Senegoid](https://sea3.discourse-cdn.com/straightdope/user_avatar/boards.straightdope.com/senegoid/32/6606_2.png) [@Senegoid](https://boards.straightdope.com/u/Senegoid)\
**Post date:** [November 12, 2012, 12:13am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/21 "2012-11-12T00:13:58Z")

</div>

> [@Derleth](#):
>
> **Senegoid** : Add a ‘return 0;’ to that and it’s golden. You can also declare iarg in the for loop preamble in the modern C standard (since C99) and as a nonstandard extension to the standard since a lot longer in compilers like gcc.

What happens normally if a C program terminates without the return 0; statement?

As for the old-style variable declaration: Like I said, I’ve had this program around since the mid-1980’s, so it still has that vintage C syntax just like it was in Charles Babbage’s day. 😃

(ETA: Actually, in its current form, it’s a hybrid old-C / new-C syntax, since the int main (…) line is clearly new-style C.)

---

<div class="post-metadata">

**Author:** ![Derleth](https://avatars.discourse-cdn.com/v4/letter/d/b9e5f3/32.png) [@Derleth](https://boards.straightdope.com/u/Derleth)\
**Post date:** [November 12, 2012, 12:29am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/22 "2012-11-12T00:29:14Z")

</div>

> [@Senegoid](#):
>
> What happens normally if a C program terminates without the return 0; statement?

Technically, it’s undefined behavior to have either ‘void main’ or to have a function declared to return ‘int’ (or any other type) that doesn’t return a value. C isn’t C++: It doesn’t do this kind of stuff for you.

Other than that, your code is perfectly valid C89, function declaration (‘int main(…)’) and all. The older function declaration style (‘int main(argc, argv)’) is pre-standard K&R C.

---

<div class="post-metadata">

**Author:** ![Digital\_is\_the\_new\_Analog](https://avatars.discourse-cdn.com/v4/letter/d/a88e4f/32.png) [@Digital\_is\_the\_new\_Analog](https://boards.straightdope.com/u/Digital_is_the_new_Analog)\
**Post date:** [November 12, 2012, 1:58am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/23 "2012-11-12T01:58:41Z")

</div>

> [@goldmund](#):
>
> Perl one-liner:
> 
> ```auto
> 
> X=5 perl -lne 'printf "%02d $_ $_ 03
> ", $ENV{X}++' filename.txt
> 
> ```
> 
> You can change the X= value to start the numbering at whatever number you choose. This will print the numbers with a minimum of 2 digits: 01, 02, 03, etc. If you would like 3, change the “%02d” to “%003d”.
> 
> Why did you want to get an initial line count for the file?

When I saw this thread, and then the awk suggestion, I remembered the days that I hung out on the usenet and someone (often Larry Wall) would come by and comment that it can be solved in one line in perl.

Glad to see the tradition is still alive. 🙂

-D/a

---

<div class="post-metadata">

**Author:** ![FuzzyOgre](https://avatars.discourse-cdn.com/v4/letter/f/a587f6/32.png) [@FuzzyOgre](https://boards.straightdope.com/u/FuzzyOgre)\
**Post date:** [November 12, 2012, 2:26am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/24 "2012-11-12T02:26:22Z")

</div>

> [@Senegoid](#):
>
> What happens normally if a C program terminates without the return 0; statement?

As someone said, it is undefined.

The reason you want to return zero is that it indicates success. In the terminal, after running an application, I can type echo $? and it returns an exit code. Zero means “all went well”.

If I try cat file.txt and press control-c before it is done, it reports 130, which means “Script terminated by Control-C”.

Rather than BASH around the bush, I’ll just say that exit codes are better than actual text messages because they are far easier to deal with in scripts. Your script can call awk and know exactly what happened by examining its return value.

A short list of exit codes and what they mean:

> **[Exit Codes With Special Meanings](https://tldp.org/LDP/abs/html/exitcodes.html)**

---

<div class="post-metadata">

**Author:** ![Senegoid](https://sea3.discourse-cdn.com/straightdope/user_avatar/boards.straightdope.com/senegoid/32/6606_2.png) [@Senegoid](https://boards.straightdope.com/u/Senegoid)\
**Post date:** [November 12, 2012, 3:53am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/25 "2012-11-12T03:53:25Z")

</div>

> [@FuzzyOgre](#):
>
> As someone said, it is undefined.
> 
> The reason you want to return zero is that it indicates success. In the terminal, after running an application, I can type echo $? and it returns an exit code. Zero means “all went well”.

Some users even go so far as to include $? in their prompt string (PS1) so that each display of the command prompt will show the exit code of the immediately preceding command.

(I always assumed that any program that terminated without an exit status, then a status of 0 would be the default result.)

ETA: Okay, I just tried that on my Ubuntu Linux mochine. Running my parg program (exactly as listed above), the resulting exit code somehow comes up as 60.

---

<div class="post-metadata">

**Author:** ![Noone\_Special](https://sea3.discourse-cdn.com/straightdope/user_avatar/boards.straightdope.com/noone_special/32/2863_2.png) [@Noone\_Special](https://boards.straightdope.com/u/Noone_Special)\
**Post date:** [November 12, 2012, 7:33am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/26 "2012-11-12T07:33:22Z")

</div>

> [@drewtwo99](#):
>
> awk ‘BEGIN{kk=$line\_number}{print kk,$0,$0,$batch\_number;kk+=1}’ filename

> [@Noone\_Special](#):
>
> I don’t remember the exact syntax offhand, but you’ll want to use sprintf instead of print – which will allow you to specify a printing format. You should use the “%s” format for your printouts of $0.

> [@drewtwo99](#):
>
> Yeah I can’t seem to make heads or tails out of the sprintf command syntax :\

OK, I know you found a work around, but if anybody is still interested…

First, my mistake, you only need _ **printf** _, not _ **sprintf** _. It’s easier. You should just use

```auto

awk 'BEGIN{kk=$line_number}{printf "%10s	%s	%s	%s
", kk,$0,$0,$batch_number;kk+=1}' filename

```

The first format segment (%10s) will print your counter as a string in a 10-character field, allowing you to align the output. The default is right-justified, and it can be overriden (left-justified) if you really want (using %-10s).

The sequences are tab characters; again, you’ll get nicer output that way.

The final "  
" is a New Line – printf doesn’t add a New Line automatically, so this is actually important.

I haven’t actually tried this out, so I could have an error in there somewhere, but this should be very close to the answer to the OP.

---

<div class="post-metadata">

**Author:** ![Senegoid](https://sea3.discourse-cdn.com/straightdope/user_avatar/boards.straightdope.com/senegoid/32/6606_2.png) [@Senegoid](https://boards.straightdope.com/u/Senegoid)\
**Post date:** [November 12, 2012, 7:49am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/27 "2012-11-12T07:49:05Z")

</div>

> [@Noone\_Special](#):
>
> OK, I know you found a work around, but if anybody is still interested…
> 
> First, my mistake, you only need _ **printf** _, not _ **sprintf** _. It’s easier. You should just use
> 
> ```auto
> 
> awk 'BEGIN{kk=$line_number}{printf "%10s	%s	%s	%s
> ", kk,$0,$0,$batch_number;kk+=1}' filename
> 
> ```
> 
> I haven’t actually tried this out, so I could have an error in there somewhere, but this should be very close to the answer to the OP.

I haven’t tried this (or anything) either, so I’m not sure if I’m right about this either, but: I suspect this needs a little more work on getting the right kind of quote marks in the right places.

With the entire one-line awk script enclosed in single-quotes like that, it will get passed exactly as-is to the awk program. (Try running the parg program, discussed above, with exactly the same line except for parg instead of awk.) In particular, I think that $line\_number and $batch\_number will not get replaced by the actual two numbers that you want to have there.

I think you need to enclose the entire awk script in double-quotes instead of single-quotes. But then, you need to do some extra back-slashing of certain characters in between those double-quotes:

```auto

awk "BEGIN{kk=$line_number}{printf \"%10s\	%s\	%s\	%s\
", kk,\$0,\$0,$batch_number;kk+=1}" filename

```

All the double-quotes, back-slashes, and _some_ of the $ symbols within the awk script need to be back-slashed.

I haven’t tried that myself (yet), but as soon as I finish posting this, I will. I plan to test it using parg, which will show me exactly how the shell ends up parsing that and passing it to the program.

These are exactly the sort of things that nobody _ever_ gets right the first time. :smack:

---

<div class="post-metadata">

**Author:** ![Senegoid](https://sea3.discourse-cdn.com/straightdope/user_avatar/boards.straightdope.com/senegoid/32/6606_2.png) [@Senegoid](https://boards.straightdope.com/u/Senegoid)\
**Post date:** [November 12, 2012, 7:58am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/28 "2012-11-12T07:58:34Z")

</div>

Okay, I tested it using parg instead of awk. I got it _this_ -----\>||\<----- _close_ to being right! There’s _one_ back-slash missing that needs to be added.

Can you find where the extra back-slash belongs?

Hint: Here’s what I got when, upon defining some values for line\_number and batch\_number, and running the _corrected_ command with parg: (Can you find the extra back-slash I added?)

```auto

$ line_number=34
$ batch_number=56
$ parg "BEGIN{kk=$line_number}{printf \"%10s\	%s\	%s\	%s\
\", kk,\$0,\$0,$batch_number;kk+=1}" filename
parg: Argument count: 3
   0: <parg>
   1: <BEGIN{kk=34}{printf "%10s	%s	%s	%s
", kk,$0,$0,56;kk+=1}>
   2: <filename>
-----------------------------------------------------------

```

Note: I think this will not preserve any leading zero digit in batch\_number! To do that, you need to get double-quote marks around the $batch\_number in the script, which will result in double-quote marks around the “56” as seen by awk or parg. That should preserve any leading zero digit. I’ll leave this as an exercise for the readers.

---

<div class="post-metadata">

**Author:** ![Senegoid](https://sea3.discourse-cdn.com/straightdope/user_avatar/boards.straightdope.com/senegoid/32/6606_2.png) [@Senegoid](https://boards.straightdope.com/u/Senegoid)\
**Post date:** [November 12, 2012, 8:08am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/29 "2012-11-12T08:08:25Z")

</div>

But wait! There’s more!

Do the eight-digit numbers on the input lines ever have leading zero digits? If so, I think those may get lost too! Has anyone checked out that case yet?

**drewtwo99** , do you ever have that in your data files? Have you tried a test case with any leading zeros in your input data?

If that problem arises, and any of the above awk scripts lose the leading zeros (like they do with that two-digit number), then you need to fix that too. I think you can fix it just the same way as I suggested above for the two-digit number at the end.

ETA: P.S.: In awk, is printf a command or a function? That is, do the arguments to the printf need to be enclosed in parentheses like they would be in C? (IIRC, such parentheses are optional in awk.)

---

<div class="post-metadata">

**Author:** ![FuzzyOgre](https://avatars.discourse-cdn.com/v4/letter/f/a587f6/32.png) [@FuzzyOgre](https://boards.straightdope.com/u/FuzzyOgre)\
**Post date:** [November 12, 2012, 8:18am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/30 "2012-11-12T08:18:32Z")

</div>

> [@Senegoid](#):
>
> ETA: Okay, I just tried that on my Ubuntu Linux mochine. Running my parg program (exactly as listed above), the resulting exit code somehow comes up as 60.

I got 60 as well.

---

<div class="post-metadata">

**Author:** ![Derleth](https://avatars.discourse-cdn.com/v4/letter/d/b9e5f3/32.png) [@Derleth](https://boards.straightdope.com/u/Derleth)\
**Post date:** [November 12, 2012, 8:45am UTC](https://boards.straightdope.com/t/linux-bash-script-question/640712/31 "2012-11-12T08:45:38Z")

</div>

> [@FuzzyOgre](#):
>
> I got 60 as well.

If you’re really lucky, you’ll get demons flying out your nose.

[Previous page](https://boards.straightdope.com/t/linux-bash-script-question/640712.md?page=1)
