rca(1) General Commands Manual rca(1) NAME rca - a rich/RPN (and more) programmer's calculator SYNOPSIS rca [ initial rca command text ] DESCRIPTION rca is a command-line reverse polish notation (RPN) calculator loosely inspired by the long line of Hewlett-Packard scientific calculators. Operators include scientific, logical, and bitwise operations. rca can also evaluate traditional infix expressions, greatly expanding its usefulness. As a programmer's calculator, word width can be adjusted to emulate the arithmetic of any class of CPU. rca can also be easily incorporated into shell scripts to provide floating point support. Arithmetic is done using an arbitrary precision decimal floating point library. The default precision is 30 digits, which can be modified at startup via the environment. A complete list of operators and commands can be obtained with the help command. Whitespace in rca's input is often optional, though some cases will cause ambiguity. A # character starts a comment. The rest of the line is ignored. Depending on how rca is built, command-line editing, command history, and command completion may be available, using either the editline or readline library. REVERSE POLISH NOTATION Numbers entered by the user are pushed onto a stack. An operator pops those stack entries, usually 1 or 2 at a time, and pushes the result of the operation back on the stack. There are operators for the usual arithmetic operations (+, -, etc), functions (sin, cos, sqrt, etc), bit-shifting and manipulation (<<, >>, &, |, etc), logical operations (&&, ||), and comparators (==, !=, <=, etc). There are also unit conversions available (i2mm, oz2g, f2c, and more). The top two elements on the stack, in HP tradition, are sometimes referred to in the documentation as x and y, but not literally within the program itself with two exceptions: the lastx and lasty (or lx and ly) operators return the value that was at the top and next-to-top of stack, just previous to the most recently executed operator. The value at the top of the stack can be shown with the p command, and the entire stack with P. When rca prints the stack, the "top" of the stack is printed last, i.e., closest to the bottom of the screen. Autoprinting will print the value at the top of the stack after most input lines. This is on by default; it can be toggled off with 0 autoprint (or 0 ap). INFIX NOTATION Infix expressions in rca are translated to RPN by an implementation of Dijkstra's "shunting yard" algorithm, and then executed as usual. rca supports infix (i.e., traditional, "normal") expressions in two different ways: as "transient" additions to the stream of RPN command input, and as a full-time replacement for that stream. Transient infix expressions must be fully enclosed in parentheses, and cannot cross to a new line. A single line of input can be a mix of RPN notation (unparenthesized) and complete infix expressions (parenthesized). The infix expressions "escape" the RPN model, but evaluate to a single result, which is pushed onto the RPN stack as if the infix expression were a single operator. Full-time infix mode is turned on/off with the 0/1 infix toggle command. When infix mode is enabled (using 1 infix), all input is taken as infix expressions. No outer enclosing parentheses are required. More than one expression per line can be separated by ';'. (See below.) A single expression must start and end on the same line of input. Since infix expressions are incompatible with the rca commands for printing, quitting, configuration, etc, those commands (and any other valid RPN) must be entered following a : (colon) character. In full-time infix mode, use :q to quit, :p to print, :config to view configuration, :H zf ra to switch to hex mode with zero-fill and right alignment, etc. All infix expressions put a result on the stack, so while in full-time infix mode, the stack will slowly grow. It can be viewed, of course, with :P. Use :0 infix to leave full-time infix mode. Infix expressions are evaluated with fairly typical rules of precedence (see OPERATOR PRECEDENCE below). All input number formats are accepted in infix, just as in RPN. All rca stack operators can be used as infix functions, including the unary operators (i.e., -x +x ~x !x), and all of the comparison, logical, and bitwise operators. Infix expressions result in a value pushed onto the stack: (-3 + 5) will push the value 2. With single operand operators, the operand always follows the operator. For two operand operators, one operand is placed to either side. Exponentiation would be written as ( 3 ** 2 ), (giving 9), and bit-setting as (2 setb 3) (giving 0x0a, or 10). The expression (sin 180 == cos 90) yields the value 1, i.e. "true". The lastx and lasty (or lx and ly) operators can be used in an infix expression. They return the value of x and y (i.e., the top two values on the stack) prior to the expression being invoked. This can be convenient for chained calculations: if several infix expressions are evaluated in a row, the value of lx in each will always be the the result of the previous. In turn, ly will be the result of the second previous expression. Also, after RPN: 3 4 * (lx + ly) will leave 12 and 7 on the stack.) Variables, named with a leading '_' (underscore), like _a, _tmp, or _my_var, can be referenced for either reading or writing. See the SPECIAL VALUES AND VARIABLES section, below. Multiple sub-expressions separated by ';' (semicolon) can be enclosed in a single pair of parentheses (or share a single line, in full-time infix mode). The result of the parenthesized expression (or line) is the result of the last such sub- expression. The primary use of ';' is likely for expressions which assign to variables. See the example in the SPECIAL VALUES AND VARIABLES section, below. In RPN ';' discards the top stack element, like pop. If an error occurs during evaluation of an infix expression, evaluation will cease, and the stack is left as it was at the point of the error. OPERATING MODES rca can be configured into two main modes of operation: floating point (the default) using the F command, and integer, using one of D (signed decimal), H (hex), O (octal), or B (binary). "Currency" mode, selected with C, is a floating point mode tuned for working with a fixed number of decimal places. Math is always performed using signed arithmetic in all modes, and most math is done using multi-precision floating point "decimal" operands. The system's floating point unit is not used. In integer mode, all stack values are masked to the currently set word width, and fractional parts are discarded. The various integer modes differ only in how values are displayed by default. In currency mode, all new stack values are rounded to 2 decimal places before being pushed to the stack, and are displayed in a fixed, 2 decimal place format. Existing stack values are not modified. The '2' comes from the current locale's "frac_digits" element, so may vary in different countries. Rounding, as elsewhere in rca, is "half-up", not "half-even" as is often used in financial software. The default printing format, as determined by the current calculator mode (i.e., F, D, H, O, B, C), is used by the p, P, and autoprint commands. Regardless of the current mode, individual values can also be viewed in any format, from any mode, by using f, d, h, o, b, u, c, or m, which correspond to the similarly named modes. When using these display commands, the value is printed as if you had entered the corresponding (uppercase) mode, including any masking due to word width. (There is no U or M mode, but the u and m commands can be used to print as unsigned decimal, or as floating point, using the maximum available number of digits.) The only way to see the entire stack in a different base is to switch to that mode. The input base of a number is independent of the calculator mode, and is controlled entirely by how it is entered: 10, 0xa, 0o12, 0b1010 and 1e01 are all the same value. The calculator mode gives no preference to how input is done: for example, hex values must include the "0x" prefix even in H mode, and "0x" may also be used when in float mode. Note that octal must be entered using the "0o" prefix, which is also how octal is printed. Input using the more traditional "0" prefix is interpreted as decimal. When entering numbers in non-decimal bases, limitations in the parser prevents those numbers from being bigger than will fit in 64 bits, or roughly 1.8e18. Floating point In floating point mode (i.e., F mode), all storage and operations use mpdecimal ("Multi-precision Decimal") operands, resulting in far more digits of accuracy than the C floating point math library would allow. (mpdecimal is also used in the integer modes, except for the bitwise operators.) Because floating point (even with decimal math) is inherently inexact, values are sometimes calculated which are almost correct (like .99999999999... instead of 1), but not quite. rca rounds to a set number of digits when displaying and comparing. See also the DATA TYPES, OVERFLOW, ACCURACY section, below. Floating point printing can be controlled by the automatic, engineering, fixed, and digits commands. With automatic (or auto), output is flexible: scientific notation (e.g., 1e09) is used when the exponent would be less than -4, or greater than the chosen number of digits (see below). Otherwise the output is a simple decimal number. engineering (or eng) is suited to engineering and science: scientific notation is always used, but only with exponents which are a multiple of 3. This allows direct reading of values that might be in units with prefixes like kilo, mega, nano, pico, etc. With fixed, rca tries to always present numbers as just a whole part and a fractional part with a fixed number of digits. This works well for values with small numbers of digits near decimal point, and is convenient for use in scripts, but gets awkward with extremely large or extremely small numbers. For very large numbers, rca will switch to 'auto' format when non-significant 0 digits begin to appear to the left of the decimal point. The digits command controls the number of digits displayed by any of the above formats. (Only display is affected: the actual number of digits/bits stored and used in computation is unaffected.) For auto and eng formats, the number configured with digits is simply the number of digits either format will display. For fixed format, it's the number of digits shown after the decimal point. digits will allow setting a value as low as 0, since this can be useful with fixed format (to print no fractional part whatever). The auto and eng formats have their own minimums (1, and 3, respectively) which they enforce silently. Requesting -1 digits will choose the calculator maximum. The maximum allowed digits value is configured when rca is built, but can be modified by setting an environment variable at startup. (See CONFIGURATION, below.) Integer Integer mode is selected with any of the following commands, which also choose the default printing format: D (signed decimal), H (hex), O (octal), or B (binary). By default the width of rca's integers is the maximum supported, but it can be configured to as few as 2 bits using the width or bits commands. Requesting a width of -1 will choose the maximum width, which is 64 bits on all supported platforms. Be aware that the argument for the width command is itself subject to restrictions placed on integers. If 2 bits is configured, undoing it requires either using -1 bits to set to the maximum, or leaving integer mode with F before adjusting the width. (The word width can also be raised incrementally.) Values are masked to the current word width for both use and display, whether they are input by the user or result from an operation. Arithmetic on all values is signed. If floating operations are used on width-restricted integers, the width restriction is ignored for the operation, but masking will happen when storing the result. Numeric separators rca can add commas (or the locale's "thousands separator") to group the numbers it prints. These separators can be toggled on or off with 0/1 sep (or separators). Separators are applied to all integer bases and floating formats, as in "3,141,593" and "0o13,767,730". The separators are strictly cosmetic, and based solely on the printed digits. No bitwise splitting (e.g., into bytes) is implied. On input, the locale's currency symbol and thousands separator are ignored, as a convenience for doing arithmetic on copy/pasted data. See the LOCALE section, below, for more detail. SPECIAL VALUES AND VARIABLES The pi and e operators push the obvious constants onto the stack. In the HP tradition, the sto ("store") operator copies x to an off-stack storage location (without disturbing the stack). rcl ("recall") fetches that value, pushing it onto the stack. These commands are largely superseded by rca variables, but are still quick and convenient. Variables are created dynamically (with a value of 0) on first reference, either by assigning a value ( _var = 42), or by using it ( _var + 17). Variables' names must start with an underscore character. In RPN, simply naming the variable will push its value to the stack. To assign to a variable in RPN, the "assign to" operator (=) must be used immediately before naming the variable. If = is not followed by a variable name, it's a no-op. (This is the only "stateful" RPN operation.) The following two sequences are equivalent. Both set 4 variables: _w, _l, _area, and _diagonal. It works best to say "assign to" for = when reading the RPN version. 3=_w 4=_l * = _area _l 2 ^ _w 2 ^ + sqrt = _diagonal and (_w=3; _l=4; _area=_l * _w; _diagonal = sqrt (_w^2 + _l^2)) Variables can be listed with variables or vars. Variables can all be discarded with clearvariables. Variables cannot be deleted individually. CONFIGURATION The config command shows a summary of the current settings in rca, along with the commands needed to recreate those settings. rca doesn't read a configuration file on startup. Instead, commands are read from the environment variable RCA_INIT, and then from any command line arguments. Initial conditions can be established by either method. Any output from commands run via $RCA_INIT is discarded. Also on startup, rca will use the $RCA_DIGITS variable to set the maximum number of displayed digits. That value cannot be set below 2, but there is no enforced maximum. (Caveat emptor.) The current built-in default is 30 digits. Many of the commands that control rca's operation and appearance have been described elsewhere, but a concise list may be useful: F, D, H, O, and B choose float or integer, and the default output base. (Startup: F) automatic (or auto) chooses a floating point format that switches between scientific notation and simple decimal based on the magnitude of the number being shown. (Startup: auto is selected.) engineering (or eng) chooses a floating point format which uses scientific notation, but only with exponents which are a multiple of 3. fixed chooses a floating point format that will never use scientific notation. digits chooses the number of digits used by the floating point formats. The maximum is the number of significant digits supported by the calculator. Selecting a count of -1 will select the calculator's maxiumum. (Startup: 6) width (or bits) chooses the size of integers, in bits. Selecting a size of -1 will select the maxiumum. (Startup: calculator maximum, likely 64). separators (or sep) toggles whether output will include separators (usually ',', but see the LOCALE section) for readability. (Startup: enabled) rightalign (or ra) toggles whether displayed values should be vertically aligned at the left margin by their first digit, or to the right, by their decimal point. (Startup: enabled) zerofill (or zf) toggles whether or not hex, octal, and binary integers are left-padded out to the chosen word width with zeros. (Startup: disabled) autoprint (or ap) toggles printing of the top of stack after newlines. (Startup: enabled) degrees toggles whether degrees are used by the trig functions, rather than radians. (Startup: enabled) infix toggles whether full-time infix mode is active or not. Use 1 infix to enable, and :0 infix to disable. (Startup: disabled) echo toggles whether input that comes from a file or pipe should be copied to stdout, allowing commands to be recorded along with their results. (Output from rca all starts with at least one space character, so input and output can usually be easily distinguished.) Unlike other rca commands, echo produces no confirmation messages. (Startup: disabled) errorexit forces rca to exit on any subsequent error. Normally errors which result from user input are reported, but operation continues. (Startup: disabled) All of the above commands will print a confirmation message, but to avoid confusion, that message will only print if the command is the last on its line of input. HELP The help or ? command gives a complete list of operators/commands. If $PAGER is set in the environment, the shell command it names is used to display the help text. (The command must read the text from standard input.) Otherwise the text is sent directly to stdout. The state command will print a summary of rca's current state. OPERATOR PRECEDENCE Infix evaluation depends on operator precedence and associativity. The precedence command lists the operators by decreasing precedence. The 'R' denotes those which are right associative. All others group left to right. (This list has no meaning for RPN.) 1 ( ; ) 2 R + - ~ ! bitc chs negate recip sqrt sin cos tan asin acos atan exp ln log2 log10 abs frac int i2mm mm2i ft2m m2ft mi2km km2mi f2c c2f oz2g g2oz oz2ml ml2oz q2l l2q d2r r2d dd2dms dms2dd mpg2l100km 3 R ^ ** 4 atan2 5 * x / mod 6 % +% -% %? 7 + - 8 >> << ror rol 9 & clearb 10 xor 11 | setb 12 < > <= >= 13 == != 14 && 15 || 16 = Like C, Java, JavaScript, and Rust (but unlike Python and bc), the ! operator (logical NOT) is a high-precedence unary operator and binds very strongly. So (!_a == _b) is the same as ((!_a) == _b). Unlike C, Java, and JavaScript (but like Ruby, Python, Rust, and bc), the bitwise operators bind more tightly than comparison operators. So (_a & _b == 5) is the same as ((_a & _b) == 5). VARIADIC OPERATORS Variadic operators use all or some of the stack, optionally stopping just before reaching a previously set "mark". They are the only operators which use more than two stack elements. Variadic operators cannot be used in an infix expression. N mark (i.e., the mark command with an argument of N) will cause a later variadic operation to consider just the current top N values, plus any further values that are pushed prior to the operation. N cannot be greater than the depth of the stack. 0 mark sets the mark at the current top of stack, causing only subsequent pushes to be included by a later variadic. -1 mark will clear the mark. If set, the position of the mark is shown when the full stack is printed. snapshot is variadic, and will make a copy of the stack up to the mark or the end of stack. The copied entries are undisturbed. Its complement, restore, will set the stack mark at the top of stack, and then push the entire saved snapshot. (The mark is set as a convenience for later use of the restored entries.) A full exact copy of the stack is ensured by -1 mark snapshot followed later by clear restore. The clearsnapshot command will discard any existing snapshot. sum, avg, and stddev are variadics which calculate the total, the mean, and the sample standard deviation of stack entries up to the mark or the end of stack. The entries are removed, and are replaced by the result. As a convenience, these commands will attempt a snapshot before proceeding, but won't overwrite an existing snapshot. Always doing a manual snapshot is safest, but it can be skipped if only working with one set of data. 1 3 7 10 snapshot avg restore stddev will leave the average and standard deviation of the given list on the stack. OPERATOR NOTES Most operators behave as they are commonly understood to. A few need more specific documentation. In rca's infix expressions, exponentiation (^ or **) is right associative, and has lower precedence than unary minus. Each of these lines returns a result of 1 (true): ((2 ^ 3 ^ 2) == (2 ^ (3 ^ 2))) # i.e., 512 ((-3 ^ 2) == ((-3) ^ 2))) # i.e., 9 mod (modulo) is a floating point operation, not integer. frac applied to negative values will give a negative result. There are several two-operand percentage operators: % gives x % of y (or vice versa, of course, since it's commutative). +% and -% give y plus or minus x percent of y. So 50 17 +% results in 58.5. %? gives the inverse of those, i.e., the delta percentage: 50 58.5 %? results in 17. In an infix expression, operators with two arguments expect them to the left and right. This is intuitive for symbolic operators (as in 1 + 2 ), but for named operators it can look odd. (0xf0 setb 3) sets bit 3 in 0xf0. atan2 works similarly. This expression: (sin 30 atan2 cos 30) could also be written as ((sin 30) atan2 (cos 30)) and will evaluate to "30". (In RPN, this would be 30 sin 30 cos atan2.) The trigonometric functions (sin, cos, tan, asin, acos, atan, and atan2) take and return angles in degrees by default. 0 degrees will switch them to radians, and 1 degrees will switch them back. Also, the d2r/r2d operators convert the angle units directly. Bitwise operations (~ <<, >>, &, |, xor, clearb, and setb) convert their operands to integer first, regardless of mode. As might be expected, these operations will discard fractional parts, and may discard digits. Bitwise operations will not execute, and will cause an error, if either operand will not fit in a long long. dd2dms and dms2dd convert between decimal degrees and degrees/minutes/seconds. The d/m/s format (ab)uses the floating point format: a) whole degrees are left alone, b) minutes use the two digits immediately following the decimal, c) seconds (and fractions) come next, starting at the "thousandths" digit. So 40°41′21.3″N, 74°2′40″W would be expressed as 40.41213 and -74.0240 in DMS, and the dms2dd operator would convert them to 40.6892 and -74.0444 in decimal degrees. Of course, this conversion can also be used for time values expressed in hours, minutes, and seconds. Use dd2dms with "fixed" display mode, and with at least 4 fractional digits, to ensure seeing the DMS format correctly. nop does nothing. If used as the last command on a line, nop has the side effect of suppressing normal printed output, which can be useful in scripts. The : (colon) command does nothing, but signifies to the parser that the rest of the line should be interpreted as RPN. This is needed when in full-time infix mode, to accomplish printing and mode changing, or to quit. LOCALE The locale is consulted for just a few things: the decimal point, the thousands separator and grouping specification, the currency symbol, and the number of fractional digits used for currency. If using the minimal C/POSIX locale, defaults are provided: the thousands separator is set to ',' (at every 3 digits), fractional digits are set to 2, and the currency symbol to '$'. The locale always chooses the decimal point. Usually this is '.', but is also commonly ','. The thousands separator is stripped from all input, and on output will optionally be used for numeric grouping. The currency symbol is checked to see if its value occurs anywhere in the name of any rca command or operator. If not, it is stripped from all input. DATA TYPES, OVERFLOW, ACCURACY All stack values in rca are stored in mpdecimal format. This is convenient for a calculator which will primarily deal with floating point, but can affect rca's mixed model. Changing rca's operating mode from floating point to an integer mode requires conversion of all stack values to integer. If the conversion from mpdecimal to long long can't be done without loss, a message is issued, but the conversion has already occurred. (The message shows the value with enough digits that it can be restored accurately via copy and paste.) If the conversion occurred while simply displaying a float as integer, without changing modes, then the original value is unchanged. Execution will proceed after the warning unless errorexit has been enabled. Some floating point operations give results which are invalid: "nan" (i.e., "not a number"), or "+inf" or "-inf" (i.e., infinity). When converting to integer mode, these values are preserved, along with their semantics: any computation involving nan will return nan, and any conditionals involving nan will return false. rca doesn't distinguish between mathematical poles (e.g., the value of "tan(pi/2)") and overflow conditions (very large finite values that could be represented, if only you'd bought a better calculator). Both show as "+/-inf". Floating point math by its nature is imprecise. It's not uncommon for small rounding errors, and errors introduced by the necessary truncations to change values in obvious ways. Something that should be 0 may instead have a very tiny value, or two numbers which should be equal may differ by an insignificant amount. rca helps by rounding displayed values to rca's maximum precision. The internal representation (using a few digits more) of these values remains unchanged -- only the printed output (or the comparison) is affected. Rounding in rca is always "half-up". That is, when rounding a value exactly halfway between the two rounding choices, rounding goes away from zero. EXIT STATUS rca will normally exit with status 0 or 1. To satisfy normal shell boolean logic semantics, the exit status is 0 if the top of stack is non-zero, and 1 if the top of stack is 0. A normal exit with an empty stack causes an exit status of 2. Unrecoverable internal errors (e.g., failed memory allocation) cause an exit status of 3. Errors resulting from user input (parsing errors, empty stack, data conversion warnings) are non-fatal unless the errorexit toggle has been set. In that case, those warnings and errors will cause an exit status of 4. This can be useful when rca is used non-interactively. SHELL SUPPORT Incorporating rca into the shell is straightforward: # This shell snippet gives simple access to rca's floating point # capability from a POSIX shell. Use it with "source rca_float". # # After including this code, use lines like this to calculate: # foo=$(fe "$bar * pi") # or like this for a conditional expression: # if fc "(10 * 3) < $foo"; then ... # # Use RCA_INIT to set common initial conditions. Defaults are # provided here, but values set externally will override. export RCA_INIT_DEFAULTS="3digits fixed 0separators 1errorexit" _rca_run() # support routine { local output exitcode output=$( RCA_INIT="$RCA_INIT_DEFAULTS ${RCA_INIT:-}" \ rca "$*" q 2>&1 ) exitcode=$? # strip leading/trailing whitespace read -rd '' output <<< "$output" case $exitcode in 0|1) echo "$output" return $exitcode ;; esac echo "rca failure: '$output'" >&2 exit $exitcode } fe() # Evaluate a floating point expression. { _rca_run "( $* )" return 0 } fc() # Evaluate a floating point conditional expression. { _rca_run "( $* )" >/dev/null } AUTHOR Paul Fox created rca (formerly called "ca") very slowly over a span of decades, starting in 1993. version v43 Apr 9, 2026 rca(1)