1.\" $NetBSD: bc.1,v 1.12 2024/10/12 17:56:45 rillig Exp $ 2.\" 3.\" bc.1 - the bc manual 4.\" 5.\" Copyright (C) 1991-1994, 1997, 2000, 2003, 2012-2017 Free Software Foundation, Inc. 6.\" Copyright (C) 2004, 2017 Philip A. Nelson 7.\" Copyright (C) 2017 Thomas Klausner 8.\" All rights reserved. 9.\" 10.\" Redistribution and use in source and binary forms, with or without 11.\" modification, are permitted provided that the following conditions 12.\" are met: 13.\" 1. Redistributions of source code must retain the above copyright 14.\" notice, this list of conditions and the following disclaimer. 15.\" 2. Redistributions in binary form must reproduce the above copyright 16.\" notice, this list of conditions and the following disclaimer in the 17.\" documentation and/or other materials provided with the distribution. 18.\" 3. Neither the name of Philip A. Nelson nor the name of the Free Software 19.\" Foundation may not be used to endorse or promote products derived from 20.\" this software without specific prior written permission. 21.\" 22.\" THIS SOFTWARE IS PROVIDED BY PHILIP A. NELSON ``AS IS'' AND ANY EXPRESS OR 23.\" IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 24.\" OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 25.\" IN NO EVENT SHALL PHILIP A. NELSON OR THE FREE SOFTWARE FOUNDATION BE 26.\" LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 27.\" CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 28.\" SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 29.\" INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 30.\" CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 31.\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF 32.\" THE POSSIBILITY OF SUCH DAMAGE. 33.\" 34.\" 35.\" 36.Dd April 16, 2017 37.Dt BC 1 38.Os 39.Sh NAME 40.Nm bc 41.Nd arbitrary precision calculator language 42.Sh SYNOPSIS 43.Nm 44.Op Fl hilqsvw 45.Op long-options 46.Op Ar 47.Sh DESCRIPTION 48.Nm 49is a language that supports arbitrary precision numbers 50with interactive execution of statements. 51There are some similarities 52in the syntax to the C programming language. 53A standard math library is available by command line option. 54If requested, the math library is defined before processing any files. 55.Nm 56starts by processing code from all the files listed 57on the command line in the order listed. 58After all files have been processed, 59.Nm 60reads from the standard input. 61All code is executed as it is read. 62(If a file contains a command to halt the processor, 63.Nm 64will never read from the standard input.) 65.Pp 66This version of 67.Nm 68contains several extensions beyond traditional 69.Nm 70implementations and the POSIX draft standard. 71Command line options can cause these extensions to print a warning 72or to be rejected. 73This document describes the language accepted by this processor. 74Extensions will be identified as such. 75.Ss OPTIONS 76.Bl -tag -width "XXinteractiveXXXXXX" 77.It Fl h , Fl Fl help 78Print the usage and exit. 79.It Fl i , Fl Fl interactive 80Force interactive mode. 81.It Fl l , Fl Fl mathlib 82Define the standard math library. 83.It Fl q , Fl Fl quiet 84Quiet mode. 85.It Fl s , Fl Fl standard 86Process exactly the POSIX 87.Nm 88language. 89.It Fl v , Fl Fl version 90Print the version number and copyright and quit. 91.It Fl w , Fl Fl warn 92Give warnings for extensions to POSIX 93.Nm . 94.El 95.Ss NUMBERS 96The most basic element in 97.Nm 98is the number. 99Numbers are arbitrary precision numbers. 100This precision is both in the integer 101part and the fractional part. 102All numbers are represented internally 103in decimal and all computation is done in decimal. 104(This version of 105.Nm 106truncates results from divide and multiply operations.) 107There are two attributes of numbers, the length and the scale. 108The length is the 109total number of significant decimal digits in a number and the scale 110is the total number of decimal digits after the decimal point. 111For example: 112.Pp 113.Bl -inset -offset indent -compact 114.It Li .000001 115has a length of 6 and scale of 6. 116.It Li 1935.000 117has a length of 7 and a scale of 3. 118.El 119.Ss VARIABLES 120Numbers are stored in two types of variables, simple variables and 121arrays. 122Both simple variables and array variables are named. 123Names begin with a letter followed by any number of letters, digits and 124underscores. 125All letters must be lower case. 126(Full alpha-numeric names are an extension. 127In POSIX 128.Nm 129all names are a single lower case letter.) 130The type of variable is clear by the context 131because all array variable names will be followed by brackets 132.Pq Ql [] . 133.Pp 134There are four special variables, 135.Ic scale , 136.Ic ibase , 137.Ic obase , 138and 139.Ic last . 140.Ic scale 141defines how some operations use digits after the decimal point. 142The default value of 143.Ic scale 144is 0. 145.Ic ibase 146and 147.Ic obase 148define the conversion base for input and output numbers. 149The default for both input and output is base 10. 150.Ic last 151(an extension) is a variable that has the value of the last 152printed number. 153These will be discussed in further detail where appropriate. 154All of these variables may have values assigned to them 155as well as used in expressions. 156.Ss COMMENTS 157Comments in 158.Nm 159start with the characters 160.Ql /* 161and end with the characters 162.Ql */ . 163Comments may start anywhere and appear as a single space in the input. 164(This causes comments to delimit other input items. 165For example, a comment can not be found in the middle of 166a variable name.) 167Comments include any newlines (end of line) between 168the start and the end of the comment. 169.Pp 170To support the use of scripts for 171.Nm , 172a single line comment has been added as an extension. 173A single line comment starts at a 174.Ql # 175character and continues to the next end of the line. 176The end of line 177character is not part of the comment and is processed normally. 178.Ss EXPRESSIONS 179The numbers are manipulated by expressions and statements. 180Since the language was designed to be interactive, statements and expressions 181are executed as soon as possible. 182There is no 183.Dq main 184program. 185Instead, code is executed as it is encountered. 186(Functions, discussed in 187detail later, are defined when encountered.) 188.Pp 189A simple expression is just a constant. 190.Nm 191converts constants 192into internal decimal numbers using the current input base, specified 193by the variable 194.Ic ibase . 195(There is an exception in functions.) 196The legal values of 197.Ic ibase 198are 2 through 36. 199(Base values greater than 16 are an extension.) 200Assigning a value outside this range to 201.Ic ibase 202will result in a value of 2 or 36. 203Input numbers may contain the characters 0-9 and A-Z. 204(Note: They must be capitals. 205Lower case letters are variable names.) 206Single digit numbers always 207have the value of the digit regardless of the value of 208.Ic ibase . 209(i.e.\& 210.Ql A 211=\~10.) 212For multi-digit numbers, 213.Nm 214changes all input digits greater or equal to ibase to the value of 215.Ic ibase - 1 . 216This makes the number 217.Ql ZZZ 218always be the largest 3 digit number of the input base. 219.Pp 220Full expressions are similar to many other high level languages. 221Since there is only one kind of number, there are no rules for mixing 222types. 223Instead, there are rules on the scale of expressions. 224Every expression has a scale. 225This is derived from the scale of original 226numbers, the operation performed and in many cases, the value of the 227variable 228.Ic scale . 229Legal values of the variable 230.Ic scale 231are 0 to the maximum number representable by a C integer. 232.Pp 233In the following descriptions of legal expressions, 234.Ar expr 235refers to a complete expression and 236.Ar var 237refers to a simple or an array variable. 238A simple variable is just a 239.Dq Ar name 240and an array variable is specified as 241.Do Ar name Ns Ic \&[ Ns Ar expr Ns Ic \&] Dc . 242Unless specifically mentioned the scale of the result is the maximum scale of the 243expressions involved. 244.Bl -tag -width 15n 245.It Ic \&- Ns Ar expr 246The result is the negation of the expression. 247.It Ic \&++ Ns Ar var 248The variable is incremented by one and the new value is the result of 249the expression. 250.It Ic \&-- Ns Ar var 251The variable is decremented by one and the new value is the result of the 252expression. 253.It Ar var Ns Ic \&++ 254The result of the expression is the value of 255the variable and then the variable is incremented by one. 256.It Ar var Ns Ic \&-- 257The result of the expression is the value of the variable and then 258the variable is decremented by one. 259.It Ar expr Ic \&+ Ar expr 260The result of the expression is the sum of the two expressions. 261.It Ar expr Ic \&- Ar expr 262The result of the expression is the difference of the two expressions. 263.It Ar expr Ic \&* Ar expr 264The result of the expression is the product of the two expressions. 265.It Ar expr Ic \&/ Ar expr 266The result of the expression is the quotient of the two expressions. 267The scale of the result is the value of the variable 268.Ic scale . 269.It Ar expr Ic \&% Ar expr 270The result of the expression is the remainder and it is computed in the 271following way: 272To compute a%b, first a/b is computed to 273.Ic scale 274digits. 275That result is used to compute a-(a/b)*b to the scale of the 276maximum of 277.Ic scale + 278scale(b) and scale(a). 279If 280.Ic scale 281is set to zero and both expressions are integers this expression is the 282integer remainder function. 283.It Ar expr Ic \&^ Ar expr 284The result of the expression is the value of the first raised to the 285second. 286The second expression must be an integer. 287(If the second expression is not an integer, a warning is generated and the 288expression is truncated to get an integer value.) 289The scale of the result is 290.Ic scale 291if the exponent is negative. 292If the exponent is positive, the scale of the result is the minimum of 293the scale of the first expression times the value of the exponent and 294the maximum of 295.Ic scale 296and the scale of the first expression. 297(e.g. scale(a^b) = min(scale(a)*b, 298.No max( Ns Ic scale , 299scale(a))).) 300It should be noted 301that expr^0 will always return the value of 1. 302.It Ic \&( Ns Ar expr Ns Ic \&) 303This alters the standard precedence to force the evaluation of the 304expression. 305.It Ar var Ic \&= Ar expr 306The variable is assigned the value of the expression. 307.It Ar var Ao Ns Ar op Ns Ac Ns Ic \&= Ar expr 308This is equivalent to 309.Ar var Ic \&= Ar var Ao Ns Ar op Ns Ac Ar expr 310with the exception that the 311.Ar var 312part is evaluated only once. 313This can make a difference if 314.Ar var 315is an array. 316.El 317.Pp 318Relational expressions are a special kind of expression 319that always evaluate to 0 or 1, 0 if the relation is false and 1 if 320the relation is true. 321These may appear in any legal expression. 322(POSIX 323.Nm 324requires that relational expressions are used only in 325.Ic if , 326.Ic while , 327and 328.Ic for 329statements and that only one relational test may be 330done in them.) 331The relational operators are: 332.Bl -tag -width 15n 333.It Ar expr\s-2\d\fR1\fP\u\s+2 Ic \&< Ar expr\s-2\d\fR2\fP\u\s+2 334The result is 1 if 335.Ar expr\s-2\d\fR1\fP\u\s+2 336is strictly less than 337.Ar expr\s-2\d\fR2\fP\u\s+2 . 338.It Ar expr\s-2\d\fR1\fP\u\s+2 Ic \&<= Ar expr\s-2\d\fR2\fP\u\s+2 339The result is 1 if 340.Ar expr\s-2\d\fR1\fP\u\s+2 341is less than or equal to 342.Ar expr\s-2\d\&2\u\s+2 . 343.It Ar expr\s-2\d\fR1\fP\u\s+2 Ic \&> Ar expr\s-2\d\fR2\fP\u\s+2 344The result is 1 if 345.Ar expr\s-2\d\fR1\fP\u\s+2 346is strictly greater than 347.Ar expr\s-2\d\&2\u\s+2 . 348.It Ar expr\s-2\d\fR1\fP\u\s+2 Ic \&>= Ar expr\s-2\d\fR2\fP\u\s+2 349The result is 1 if 350.Ar expr\s-2\d\fR1\fP\u\s+2 351is greater than or equal to 352.Ar expr\s-2\d\&2\u\s+2 . 353.It Ar expr\s-2\d\fR1\fP\u\s+2 Ic \&== Ar expr\s-2\d\fR2\fP\u\s+2 354The result is 1 if 355.Ar expr\s-2\d\fR1\fP\u\s+2 356is equal to 357.Ar expr\s-2\d\&2\u\s+2 . 358.It Ar expr\s-2\d\fR1\fP\u\s+2 Ic \&!= Ar expr\s-2\d\fR2\fP\u\s+2 359The result is 1 if 360.Ar expr\s-2\d\fR1\fP\u\s+2 361is not equal to 362.Ar expr\s-2\d\&2\u\s+2 . 363.El 364.Pp 365Boolean operations are also legal. 366(POSIX 367.Nm 368does 369.Em NOT 370have boolean operations.) 371The result of all boolean operations are 0 and 1 372(for false and true) as in relational expressions. 373The boolean 374operators are: 375.Bl -tag -width 15n 376.It Ic \&! Ns Ar expr 377The result is 1 if 378.Ar expr 379is 0. 380.It Ar expr Ic \&&& Ar expr 381The result is 1 if both expressions are non-zero. 382.It Ar expr Ic \&|| Ar expr 383The result is 1 if either expression is non-zero. 384.El 385.Pp 386The expression precedence is as follows: (lowest to highest) 387.Bl -enum -offset indent 388.It 389.Ql || 390operator, left associative 391.It 392.Ql && 393operator, left associative 394.It 395.Ql \&! 396operator, nonassociative 397.It 398Relational operators, left associative 399.It 400Assignment operator, right associative 401.It 402.Ql + 403and 404.Ql - 405operators, left associative 406.It 407.Ql * , 408.Ql / 409and 410.Ql % 411operators, left associative 412.It 413.Ql ^ 414operator, right associative 415.It 416unary 417.Ql - 418operator, nonassociative 419.It 420.Ql ++ 421and 422.Ql -- 423operators, nonassociative 424.El 425.Pp 426This precedence was chosen so that POSIX compliant 427.Nm 428programs will run correctly. 429This will cause the use of the relational and logical operators to 430have some unusual behavior when used with assignment expressions. 431Consider the expression: 432.Dl a = 3 < 5 433.Pp 434Most C programmers would assume this would assign the result of 435.Dq Li 3 < 5 436(the value 1) to the variable 437.Va a . 438What this does in 439.Nm 440is assign the value 3 to the variable 441.Va a 442and then compare 3 to 5. 443It is best to use parentheses when using relational and logical operators 444with the assignment operators. 445.Pp 446There are a few more special expressions that are provided in 447.Nm . 448These have to do with user defined functions and standard functions. 449They all appear as 450.Do Ar name Ns Ic \&( Ns Ar parameters Ns Ic \&) Dc . 451See the section on functions for user defined functions. 452The standard functions are: 453.Bl -tag -width 20n 454.It Fn length expression 455The value of the length function is the number of significant digits in the 456expression. 457.It Fn read 458The read function (an extension) will read a number from the standard 459input, regardless of where the function occurs. 460Beware, this can cause problems with the mixing of data and program in 461the standard input. 462The best use for this function is in a previously written program that 463needs input from the user, but never allows program code to be input 464from the user. 465The value of the read function is the number read from 466the standard input using the current value of the variable 467.Ic ibase 468for the conversion base. 469.It Fn scale expression 470The value of the scale function is the number of digits after the decimal 471point in the expression. 472.It Fn sqrt expression 473The value of the sqrt function is the square root of the expression. 474If 475the expression is negative, a run time error is generated. 476.El 477.Ss STATEMENTS 478Statements (as in most algebraic languages) provide the sequencing of 479expression evaluation. 480In 481.Nm 482statements are executed 483.Dq as soon as possible . 484Execution happens when a newline in encountered and 485there is one or more complete statements. 486Due to this immediate 487execution, newlines are very important in 488.Nm . 489In fact, both a 490semicolon and a newline are used as statement separators. 491An improperly placed newline will cause a syntax error. 492Because newlines 493are statement separators, it is possible to hide a newline by using 494the backslash character. 495The sequence 496.Dq Ic \e Ns Ao nl Ac , 497where 498.Aq nl 499is the newline appears to 500.Nm 501as whitespace instead of a newline. 502A statement list is a series of statements separated by semicolons and 503newlines. 504The following is a list of 505.Nm 506statements and what they do: 507(Things enclosed in brackets 508.Pq Oo Oc 509are optional parts of the 510statement.) 511.Bl -tag -width 15n 512.It Ar expression 513This statement does one of two things. 514If the expression starts with 515.Ao Ar variable Ac Ao Ar assignment Ac ... , 516it is considered to be an assignment statement. 517If the expression is not an assignment statement, the 518expression is evaluated and printed to the output. 519After the number is printed, a newline is printed. 520For example, 521.Dq Li a=1 522is an assignment statement and 523.Dq Li (a=1) 524is an expression that has an embedded assignment. 525All numbers that are printed are printed in the base 526specified by the variable 527.Ic obase . 528The legal values for 529.Ic obase 530are 2 through 531.Dv BC_BASE_MAX . 532(See the section 533.Sx LIMITS . ) 534For bases 2 through 16, the usual method of writing numbers is used. 535For bases greater than 16, 536.Nm 537uses a multi-character digit method of printing the numbers where each 538higher base digit is printed as a base 10 number. 539The multi-character digits are separated by spaces. 540Each digit contains the number of characters required to represent the 541base ten value of 542.Dq Ic obase-1 . 543Since numbers are of arbitrary 544precision, some numbers may not be printable on a single output line. 545These long numbers will be split across lines using the 546.Ql \e 547as the last character on a line. 548The maximum number of characters printed 549per line is 70. 550Due to the interactive nature of 551.Nm bc , 552printing a number causes the side effect of assigning the printed value to the 553special variable 554.Ic last . 555This allows the user to recover the last value printed without having 556to retype the expression that printed the number. 557Assigning to 558.Ic last 559is legal and will 560overwrite the last printed value with the assigned value. 561The newly assigned value will remain until the next number is printed 562or another value is assigned to 563.Ic last . 564(Some installations may allow the 565use of a single period 566.Pq Ql \&. 567which is not part of a number as a short hand notation for 568.Ic last . ) 569.It Ic \*q Ns Ar string\| Ns Ic \*q 570The 571.Ar string 572is printed to the output. 573Strings start with a double quote 574character and contain all characters until the next double quote character. 575All characters are taken literally, including any newline. 576No newline character is printed after the string. 577.It Ic print Ar list 578The 579.Ic print 580statement (an extension) provides another method of output. 581The 582.Ar list 583is a list of strings and expressions separated by commas. 584Each string or expression is printed in the order of the list. 585No terminating newline is printed. 586Expressions are evaluated and their 587value is printed and assigned to the variable 588.Ic last . 589Strings in the 590.Ic print 591statement are printed to the output and may contain special characters. 592Special characters start with the backslash character 593.Pq Ql \e . 594The special characters recognized by 595.Nm 596are 597.Ql a 598(alert or bell), 599.Ql b 600(backspace), 601.Ql f 602(form feed), 603.Ql n 604(newline), 605.Ql r 606(carriage return), 607.Ql q 608(double quote), 609.Ql t 610(tab), and 611.Ql \e 612(backslash). 613Any other character following the backslash will be ignored. 614.It Ic \&{ Ar statement_list Ic \&} 615This is the compound statement. 616It allows multiple statements to be grouped together for execution. 617.It Ic if \&( Ns Ar expression Ns Ic \&) Ar statement\s-2\d\fR1\fP\u\s+2 \ 618 Oo Ic else Ar statement\s-2\d\fR2\fP\u\s+2 Oc 619The 620.Ic if 621statement evaluates the 622.Ar expression 623and executes 624.Ar statement\s-2\d\fR1\fP\u\s+2 625or 626.Ar statement\s-2\d\fR2\fP\u\s+2 627depending on the value of the 628.Ar expression . 629If the 630.Ar expression 631is non-zero, 632.Ar statement\s-2\d\fR1\fP\u\s+2 633is executed. 634If 635.Ar statement\s-2\d\fR2\fP\u\s+2 636is present and the value of the 637.Ar expression 638is 0, then 639.Ar statement\s-2\d\fR2\fP\u\s+2 640is executed. 641(The 642.Ic else 643clause is an extension.) 644.It Ic while \&( Ns Ar expression Ns Ic \&) Ar statement 645The 646.Ic while 647statement will execute the 648.Ar statement 649while the 650.Ar expression 651is non-zero. 652It evaluates the 653.Ar expression 654before each execution of the 655.Ar statement . 656Termination of the loop is caused by a zero 657.Ar expression 658value or the execution of a 659.Ic break 660statement. 661.It Ic for \&( Ns \ 662 Oo Ar expression\s-2\d\fR1\fP\u\s+2 Oc Ns Ic \&; \ 663 Oo Ar expression\s-2\d\fR2\fP\u\s+2 Oc Ns Ic \&; \ 664 Oo Ar expression\s-2\d\fR3\fP\u\s+2 Oc Ns Ic \&) \ 665 Ar statement 666The 667.Ic for 668statement controls repeated execution of the 669.Ar statement . 670.Ar expression\s-2\d\fR1\fP\u\s+2 671is evaluated before the loop. 672.Ar expression\s-2\d\fR2\fP\u\s+2 673is evaluated 674before each execution of the 675.Ar statement . 676If it is non-zero, the 677.Ar statement 678is executed. 679If it is zero, the loop is terminated. 680After each execution of the 681.Ar statement , 682.Ar expression\s-2\d\fR3\fP\u\s+2 683is evaluated before the reevaluation of 684.Ar expression\s-2\d\fR2\fP\u\s+2 . 685If 686.Ar expression\s-2\d\fR1\fP\u\s+2 687or 688.Ar expression\s-2\d\fR3\fP\u\s+2 689are missing, nothing is evaluated at the point they would be evaluated. 690If 691.Ar expression\s-2\d\fR2\fP\u\s+2 692is missing, it is the same as substituting the value 1 for 693.Ar expression\s-2\d\fR2\fP\u\s+2 . 694(The optional expressions are an 695extension. 696POSIX 697.Nm 698requires all three expressions.) 699The following is equivalent code for the 700.Ic for 701statement: 702.Bd -literal -offset indent 703expression1; 704while (expression2) { 705 statement; 706 expression3; 707} 708.Ed 709.It Ic break 710This statement causes a forced exit of the most recent enclosing 711.Ic while 712statement or 713.Ic for 714statement. 715.It Ic continue 716The 717.Ic continue 718statement (an extension) causes the most recent enclosing 719.Ic for 720statement to start the next iteration. 721.It Ic halt 722The 723.Ic halt 724statement (an extension) is an executed statement that causes the 725.Nm 726processor to quit only when it is executed. 727For example, 728.Dl if (0 == 1) halt 729will not cause 730.Nm 731to terminate because the halt is not executed. 732.It Ic return 733Return the value 0 from a function. 734(See the section on functions.) 735.It Ic return Ic \&( Ns Ar expression Ns Ic \&) 736Return the value of the expression from a function. 737(See the section on functions.) 738As an extension, the parentheses are not required. 739.El 740.Ss PSEUDO STATEMENTS 741These statements are not statements in the traditional sense. 742They are not executed statements. 743Their function is performed at 744.Dq compile 745time. 746.Bl -tag -width 15n 747.It Ic limits 748Print the local limits enforced by the local version of 749.Nm 750This is an extension. 751.It Ic quit 752When the 753.Ic quit 754statement is read, the 755.Nm 756processor 757is terminated, regardless of where the quit statement is found. 758For example, 759.Dl if (0 == 1) quit 760will cause 761.Nm 762to terminate. 763.It Ic warranty 764Print a longer warranty notice. 765This is an extension. 766.El 767.Ss FUNCTIONS 768Functions provide a method of defining a computation that can be executed 769later. 770Functions in 771.Nm 772always compute a value and return it to the caller. 773Function definitions are 774.Dq dynamic 775in the sense that a function is 776undefined until a definition is encountered in the input. 777That definition is then used until another 778definition function for the same name is encountered. 779The new definition then replaces the older definition. 780A function is defined as follows: 781.Bd -literal -offset indent 782define name ( parameters ) { newline 783 auto_list statement_list } 784.Ed 785.Pp 786A function call is just an expression of the form 787.Do Ar name Ns Ic \&( Ns Ar parameters Ns Ic \&) Dc . 788.Pp 789Parameters are numbers or arrays (an extension). 790In the function definition, zero or more parameters are defined by 791listing their names separated by commas. 792All parameters are call by value parameters. 793Arrays are specified in the parameter definition by 794the notation 795.Do Fa name Ns Ic \&[] Dc . 796In the function call, actual parameters 797are full expressions for number parameters. 798The same notation is used 799for passing arrays as for defining array parameters. 800The named array is passed by value to the function. 801Since function definitions are dynamic, 802parameter numbers and types are checked when a function is called. 803Any mismatch in number or types of parameters will cause a runtime error. 804A runtime error will also occur for the call to an undefined function. 805.Pp 806The 807.Ar auto_list 808is an optional list of variables that are for 809.Dq local 810use. 811The syntax of the auto list (if present) is 812.Do Ic auto Ar name Ns Ic \&, Ar \&... Ns Ic \&; Dc . 813(The semicolon is optional.) 814Each 815.Ar name 816is the name of an auto variable. 817Arrays may be specified by using the 818same notation as used in parameters. 819These variables have their 820values pushed onto a stack at the start of the function. 821The variables are then initialized to zero and used throughout the 822execution of the function. 823At function exit, these variables are popped so that the original 824value (at the time of the function call) of these variables are 825restored. 826The parameters are really auto variables that are initialized to a 827value provided in the function call. 828Auto variables are different than traditional local variables 829because if function 830.Ar A 831calls function 832.Ar B , 833.Ar B 834may access function 835.Ar A Ns 's 836auto variables by just using the same name, unless function 837.Ar B 838has 839called them auto variables. 840Due to the fact that auto variables and parameters are pushed onto a 841stack, 842.Nm 843supports recursive functions. 844.Pp 845The function body is a list of 846.Nm 847statements. 848Again, statements 849are separated by semicolons or newlines. 850Return statements cause the 851termination of a function and the return of a value. 852There are two 853versions of the return statement. 854The first form, 855.Dq Ic return , 856returns the value 0 to the calling expression. 857The second form, 858.Do Ic return Ic \&( Ns Ar expression Ns Ic \&) Dc , 859computes the value of the expression 860and returns that value to the calling expression. 861There is an implied 862.Dq Li return (0) 863at the end of every function. 864This allows a function 865to terminate and return 0 without an explicit return statement. 866.Pp 867Functions also change the usage of the variable 868.Ic ibase . 869All constants in the function body will be converted using the value of 870.Ic ibase 871at the time of the function call. 872Changes of 873.Ic ibase 874will be ignored during the execution of the function except for the 875standard function 876.Fn read , 877which will always use the current value 878of 879.Ic ibase 880for conversion of numbers. 881.Pp 882Several extensions have been added to functions. 883First, the format of the definition has been slightly relaxed. 884The standard requires the 885opening brace be on the same line as the 886.Ic define 887keyword and all other parts must be on following lines. 888This version of 889.Nm 890will allow any number of newlines before and after the opening brace of the 891function. 892For example, the following definitions are legal. 893.Bd -literal -offset indent 894define d (n) { return (2*n); } 895define d (n) 896 { return (2*n); } 897.Ed 898.Pp 899Functions may be defined as 900.Ic void . 901A 902.Ic void 903funtion returns no value and thus may not be used in any place that needs 904a value. 905A 906.Ic void 907function does not produce any output when called by itself 908on an input line. 909The key word 910.Ic void 911is placed between the key word 912.Ic define 913and the function name. 914For example, consider the following session. 915.Bd -literal -offset indent 916define py (y) { print "--->", y, "<---", "\en"; } 917define void px (x) { print "--->", x, "<---", "\en"; } 918py(1) 919--->1<--- 9200 921px(1) 922--->1<--- 923.Ed 924.Pp 925Since 926.Fn py 927is not a void function, the call of 928.Ql py(1) 929prints the desired output and then prints a second line that is the value of 930the function. 931Since the value of a function that is not given an 932explicit return statement is zero, the zero is printed. 933For 934.Ql px(1) , 935no zero is printed because the function is a void function. 936.Pp 937Also, call by variable for arrays was added. 938To declare 939a call by variable array, the declaration of the array parameter in the 940function definition looks like 941.Do Fa name Ns Ic \&[] Dc . 942The call to the 943function remains the same as call by value arrays. 944.Ss MATH LIBRARY 945If 946.Nm 947is invoked with the 948.Fl l 949option, a math library is preloaded and the default scale is set to 20. 950The math functions will calculate their 951results to the scale set at the time of their call. 952The math library defines the following functions: 953.Bl -tag -width 15n 954.It Fn s x 955The sine of 956.Fa x , 957.Fa x 958is in radians. 959.It Fn c x 960The cosine of 961.Fa x , 962.Fa x 963is in radians. 964.It Fn a x 965The arctangent of 966.Fa x , 967arctangent returns radians. 968.It Fn l x 969The natural logarithm of 970.Fa x . 971.It Fn e x 972The exponential function of raising 973.Va e 974to the value 975.Fa x . 976.It Fn j n x 977The Bessel function of integer order 978.Fa n 979of 980.Fa x . 981.El 982.Sh ENVIRONMENT 983The following environment variables are processed by 984.Nm : 985.Bl -tag -width 15n 986.It Ev POSIXLY_CORRECT 987This is the same as the 988.Fl s 989option. 990.It Dv BC_ENV_ARGS 991This is another mechanism to get arguments to 992.Nm . 993The format is the same as the command line arguments. 994These arguments are processed first, so any files listed in the 995environment arguments are processed before any command line argument 996files. 997This allows the user to set up 998.Dq standard 999options and files to be 1000processed at every invocation of 1001.Nm . 1002The files in the environment variables would typically contain 1003function definitions for functions the user wants defined every time 1004.Nm 1005is run. 1006.It Dv BC_LINE_LENGTH 1007This should be an integer specifying the number of characters in an 1008output line for numbers. 1009This includes the backslash and newline characters for long numbers. 1010.El 1011.Sh EXAMPLES 1012In 1013.Pa /bin/sh , 1014the following will assign the value of 1015.Ar pi 1016to the shell variable 1017.Ar pi . 1018.Bd -literal -offset indent 1019pi=$(echo "scale=10; 4*a(1)" | bc -l) 1020.Ed 1021.Pp 1022The following is the definition of the exponential function used in the 1023math library. 1024This function is written in POSIX 1025.Nm . 1026.Bd -literal -offset indent 1027scale = 20 1028 1029/* Uses the fact that e^x = (e^(x/2))^2 1030 When x is small enough, we use the series: 1031 e^x = 1 + x + x^2/2! + x^3/3! + ... 1032*/ 1033 1034define e(x) { 1035 auto a, d, e, f, i, m, v, z 1036 1037 /* Check the sign of x. */ 1038 if (x<0) { 1039 m = 1 1040 x = -x 1041 } 1042 1043 /* Precondition x. */ 1044 z = scale; 1045 scale = 4 + z + .44*x; 1046 while (x > 1) { 1047 f += 1; 1048 x /= 2; 1049 } 1050 1051 /* Initialize the variables. */ 1052 v = 1+x 1053 a = x 1054 d = 1 1055 1056 for (i=2; 1; i++) { 1057 e = (a *= x) / (d *= i) 1058 if (e == 0) { 1059 if (f>0) while (f--) v = v*v; 1060 scale = z 1061 if (m) return (1/v); 1062 return (v/1); 1063 } 1064 v += e 1065 } 1066} 1067.Ed 1068.Pp 1069The following is code that uses the extended features of 1070.Nm 1071to implement a simple program for calculating checkbook balances. 1072This program is best kept in a file so that it can be used many times 1073without having to retype it at every use. 1074.Bd -literal -offset indent 1075scale=2 1076print "\enCheck book program!\en" 1077print " Remember, deposits are negative transactions.\en" 1078print " Exit by a 0 transaction.\en\en" 1079 1080print "Initial balance? "; bal = read() 1081bal /= 1 1082print "\en" 1083while (1) { 1084 "current balance = "; bal 1085 "transaction? "; trans = read() 1086 if (trans == 0) break; 1087 bal -= trans 1088 bal /= 1 1089} 1090quit 1091.Ed 1092.Pp 1093The following is the definition of the recursive factorial function. 1094.Bd -literal -offset indent 1095define f(x) { 1096 if (x <= 1) return (1); 1097 return (f(x-1) * x); 1098} 1099.Ed 1100.Ss EDITLINE OPTIONS 1101.Nm 1102is compiled using the 1103.Xr editline 3 1104library. 1105This allows the user to do editing of lines before sending them 1106to 1107.Nm . 1108It also allows for a history of previous lines typed. 1109This adds to 1110.Nm 1111one more special variable. 1112This special variable, 1113.Ic history 1114is the number of lines of history retained. 1115The default value of \-1 means that an unlimited 1116number of history lines are retained. 1117Setting the value of 1118.Ic history 1119to a positive number restricts the number of history 1120lines to the number given. 1121The value of 0 disables the history feature. 1122For more information, read the user manual for the 1123.Xr editline 3 1124library. 1125.Ss DIFFERENCES 1126This version of 1127.Nm 1128was implemented from the POSIX P1003.2/D11 draft and contains 1129several differences and extensions relative to the draft and 1130traditional implementations. 1131It is not implemented in the traditional way using 1132.Xr dc 1 . 1133This version is a single process which parses and runs a byte code 1134translation of the program. 1135There is an 1136.Dq undocumented 1137option 1138.Fl ( c ) 1139that causes the program to output the byte code to 1140the standard output instead of running it. 1141It was mainly used for 1142debugging the parser and preparing the math library. 1143.Pp 1144A major source of differences is extensions, where a feature is 1145extended to add more functionality and additions, where new features 1146are added. 1147The following is the list of differences and extensions. 1148.Bl -tag -width 15n 1149.It Ev LANG No environment 1150This version does not conform to the POSIX standard in the processing 1151of the 1152.Ev LANG 1153environment variable and all environment variables starting 1154with 1155.Ev LC_ . 1156.It names 1157Traditional and POSIX 1158.Nm 1159have single letter names for functions, variables and arrays. 1160They have been extended to be multi-character names that start with a letter and 1161may contain letters, numbers and the underscore character. 1162.It strings 1163Strings are not allowed to contain 1164.Tn NUL 1165characters. 1166POSIX says all characters must be included in strings. 1167.It Ic last 1168POSIX 1169.Nm 1170does not have a 1171.Ic last 1172variable. 1173Some implementations 1174of 1175.Nm 1176use the period 1177.Pq Ql \&. 1178in a similar way. 1179.It comparisons 1180POSIX 1181.Nm 1182allows comparisons only in the 1183.Ic if 1184statement, the 1185.Ic while 1186statement, and the second expression of the 1187.Ic for 1188statement. 1189Also, only one relational operation is allowed in each of those statements. 1190.It Ic if No statement , Ic else No clause 1191POSIX 1192.Nm 1193does not have an 1194.Ic else 1195clause. 1196.It Ic for No statement 1197POSIX 1198.Nm 1199requires all expressions to be present in the 1200.Ic for 1201statement. 1202.It Li && , || , \&! 1203POSIX 1204.Nm 1205does not have the logical operators. 1206.It Fn read No function 1207POSIX 1208.Nm 1209does not have a 1210.Fn read 1211function. 1212.It Ic print No statement 1213POSIX 1214.Nm 1215does not have a 1216.Ic print 1217statement . 1218.It Ic continue No statement 1219POSIX 1220.Nm 1221does not have a 1222.Ic continue 1223statement. 1224.It Ic return No statement 1225POSIX 1226.Nm 1227requires parentheses around the return expression. 1228.It array parameters 1229POSIX 1230.Nm 1231does not (currently) support array parameters in full. 1232The POSIX grammar allows for arrays in function definitions, but does 1233not provide a method to specify an array as an actual parameter. 1234(This is most likely an oversight in the grammar.) 1235Traditional implementations of 1236.Nm 1237have only call-by-value array parameters. 1238.It function format 1239POSIX 1240.Nm 1241requires the opening brace on the same line as the 1242.Ic define 1243key word and the 1244.Ic auto 1245statement on the next line. 1246.It Li =+ , =- , =* , =/ , =% , =^ 1247POSIX 1248.Nm 1249does not require these 1250.Dq old style 1251assignment operators to be defined. 1252This version may allow these 1253.Dq old style 1254assignments. 1255Use the 1256.Ic limits 1257statement to see if the installed version supports them. 1258If it does support the 1259.Dq old style 1260assignment operators, the statement 1261.Dq Li a =- 1 1262will decrement 1263.Va a 1264by 1 instead of setting 1265.Va a 1266to the value \-1. 1267.It spaces in numbers 1268Other implementations of 1269.Nm 1270allow spaces in numbers. 1271For example, 1272.Dq Li x=1 3 1273would assign the value 13 to the variable 1274.Va x . 1275The same statement 1276would cause a syntax error in this version of 1277.Nm . 1278.It errors and execution 1279This implementation varies from other implementations in terms of what 1280code will be executed when syntax and other errors are found in the 1281program. 1282If a syntax error is found in a function definition, error 1283recovery tries to find the beginning of a statement and continue to 1284parse the function. 1285Once a syntax error is found in the function, the 1286function will not be callable and becomes undefined. 1287Syntax errors in the interactive execution code will invalidate the 1288current execution block. 1289The execution block is terminated by an 1290end of line that appears after a complete sequence of statements. 1291For example, 1292.Bd -literal 1293a = 1 1294b = 2 1295.Ed 1296has two execution blocks and 1297.Bd -literal 1298{ a = 1 1299 b = 2 } 1300.Ed 1301has one execution block. 1302Any runtime error will terminate the execution 1303of the current execution block. 1304A runtime warning will not terminate the current execution block. 1305.It interrupts 1306During an interactive session, the 1307.Dv SIGINT 1308signal (usually generated by the control-C character from the 1309terminal) will cause execution of the current execution block to be 1310interrupted. 1311It will display a 1312.Dq runtime 1313error indicating which function was interrupted. 1314After all runtime structures have been cleaned up, a message will be 1315printed to notify the user that 1316.Nm 1317is ready for more input. 1318All previously defined functions remain defined and the value of all 1319non-auto variables are the value at the point of interruption. 1320All auto variables and function parameters are removed during the 1321clean up process. 1322During a non-interactive session, the 1323.Dv SIGINT 1324signal will terminate the entire run of 1325.Nm . 1326.El 1327.Ss LIMITS 1328The following are the limits currently in place for this 1329.Nm 1330processor. 1331Some of them may have been changed by an installation. 1332Use the 1333.Ic limits 1334statement to see the actual values. 1335.Bl -tag -width 15n 1336.It Dv BC_BASE_MAX 1337The maximum output base is currently set at 999. 1338The maximum input base is 16. 1339.It Dv BC_DIM_MAX 1340This is currently an arbitrary limit of 65535 as distributed. 1341Your installation may be different. 1342.It Dv BC_SCALE_MAX 1343The number of digits after the decimal point is limited to 1344.Dv INT_MAX 1345digits. 1346Also, the number of digits before the decimal point is limited to 1347.Dv INT_MAX 1348digits. 1349.It Dv BC_STRING_MAX 1350The limit on the number of characters in a string is 1351.Dv INT_MAX 1352characters. 1353.It exponent 1354The value of the exponent in the raise operation 1355.Pq Ql ^ 1356is limited to 1357.Dv LONG_MAX . 1358.It variable names 1359The current limit on the number of unique names is 32767 for each of 1360simple variables, arrays and functions. 1361.El 1362.Sh DIAGNOSTICS 1363If any file on the command line can not be opened, 1364.Nm 1365will report 1366that the file is unavailable and terminate. 1367Also, there are compile 1368and run time diagnostics that should be self-explanatory. 1369.Sh HISTORY 1370This man page documents bc version nb1.0. 1371.Sh AUTHORS 1372.An Philip A. Nelson Aq Mt phil@NetBSD.org 1373.Ss ACKNOWLEDGEMENTS 1374The author would like to thank Steve Sommars for his extensive help in 1375testing the implementation. 1376Many great suggestions were given. 1377This is a much better product due to his involvement. 1378.Sh BUGS 1379Error recovery is not very good yet. 1380