onfig to print the config values and parameters thanks to Ernest Bowen . Added show objtypes to print the defined objects thanks to Ernest Bowen . Added more builtin function help files. Fixed the 3rd arg usage of the root builtin. Expanded the regress.cal regression test suite. Fixed -- and ++ with respect to objects and assignment (see the 2300 series in regress.cal). Added isident(m) to determine if m is an identity matrix. The append(), insert() and push() builtins can now append between 1 to 100 values to a list. Added reverse() and join() builtins to reverse and join lists thanks to Ernest Bowen . Added sort() builtin to sort lists thanks to Ernest Bowen . Added head(), segment() and tail() builtins to return the head, middle or tail of lists thanks to Ernest Bowen . Added more and fixed some help files. The builtin help file is generated by the help makefile. Thus it will reflect the actual calc builtin list instead of the last time someone tried to update it correctly. :-) Fixed non-standard void pointer usage. Fixed base() bug with regards to the default base. Renamed MATH_PROTO() and HIST_PROTO() to PROTO(). Moved PROTO() into prototype.h. Fixed many function prototypes. Calc does not declare functions as static in one place and extern in another. Where reasonable function prototypes were added. Several arg mismatch problems were fixed. Added support for SGI MIPSpro C compiler. Changes the order that args are declared to match the order of the function. Some source tools got confused when: arg order did not match as in: void funct(foo,bar) int bar; /* this caused a problem */ char *foo; /* even though it should not! */ { } The following are the changes from calc version 2.9.3t8 to 2.9.3t9.2: Use of the macro zisleone(z) has been clarified. The zisleone(z) macro tests if z <= 1. The macro zisabsleone(z) tests of z is 1, 0 or -1. Added zislezero(z) macro. Bugs are related to this confusion have been fixed. Added zge64b(z) macro to zmath.h. Added the macro zgtmaxufull(z) to determine if z will fit into a FULL. Added the macro zgtmaxlong(z) to determine if z will fit into a long. Added the macro zgtmaxulong(z) to determine if z will fit into a unsigned long. Added the macro ztoulong(z) to convert an absolute value of a ZVALUE to an unsigned long, or to convert the low order bits of a ZVALUE. Added the macro ztolong(z) to convert an absolute value of a ZVALUE to an long, or to convert the low order bits of a ZVALUE. Some non-ANSI C compilers define __STDC__ to be 0, whereas all ANSI C compiles define it as non-zero. Code that depends on ANSI C now uses #if defined(__STDC__) && __STDC__ != 0. Fixed ptest(a,b) bug where (a mod 2^32) < b. Previously ptest() incorrectly returned 1 in certain cases. The second ptest() argument, which is now optional, defaults to 1. This ptest(x) is the same as ptest(x,1). Added an optional 3rd argument to ptest(). The 3rd arg tells how many tests to skip. Thus ptest(a,10) performs the same probabilistic tests as ptest(a,3) and ptest(a,7,3). The ptest() builtin by default will determine if a value is divisible by a trivial prime. Thus, ptest(a,0) will only perform a quick trivial factor check. If the test count is < 0, then this trivial factor check is omitted. Thus ptest(a,10) performs the same amount of work as ptest(a,3) and ptest(a,-7,3) and the same amount of work as ptest(a,-3) and ptest(a,7,3). Added nextcand(a[,b[,c]]) and prevcand(a[,b[,c]]) to search for the next/previous value v > a (or v < a) that passes ptest(v[,b[,c]]). The nextcand() and prevcand() builtins take the same arguments as ptest(). Added nextprime(x) and and prevprime(x) return the next and previous primes with respect to x respectively. As of this release, x must be < 2^32. With one argument, they will return an error if x is out of range. With two arguments, they will not generate an error but instead will return y. Fixed some memory leaks, particularly those related with pmod(). Fixed some of the array bounds reference problems in domult(). Added a hack-a-round fix for the uninitialized memory reference problems in zsquare/dosquare. The LIBRARY file has been updated to include a note about calling zio_init() first. Also some additional useful macros have been noted. The lfactor() function returns -1 when given a negative value. It will not search for factors beyond 2^32 or 203280221 primes. Performance of lfactor() has been improved. Added factor(x,y) to look for the smallest factor < min(sqrt(x),y). Added libcalcerr.a for a math_error() routine for the convince of progs that make use of libcalc.a. This routine by default will print an message on stderr and exit. It can also be made to longjump instead. See the file LIBRARY under ERROR HANDING. Added isprime() to test if a value is prime. As of this release, isprime() is limited to values < 2^32. With one argument, isprime(x) will return an error if x is out of range. With two arguments, isprime(x,y) will not generate an error but instead will return y. Added pix(x) to return the number of primes <= x. As of this release, x must be < 2^32. With one argument, pix(x) will return an error if x is out of range. With two arguments, pix(x,y) will not generate an error but instead will return y. Fixed the way *.h files are formed. Each file guards against multiple inclusion. Fixed numeric I/O on 64 bit systems. Previously the print and constant conversion routines assumed a base of 2^16. Added support for 'long long' type. If the Makefile is setup with 'LONGLONG_BITS=', then it will attempt to detect support for the 'long long' type. If the Makefile is setup with 'LONGLONG_BITS=64', then a 64 bit 'long long' is assumed. Currently, only 64 bit 'long long' type is supported. Use of 'long long' allows one to double the size of the internal base, making a number of computations much faster. If the Makefile is setup with 'LONGLONG_BITS=0', then the 'long long' type will not be used, even if the compiler supports it. Fixed avg() so that it will correctly handle matrix arguments. Fixed btrunc() limit. The ord("string") function can now take a string of multiple characters. However it still will only operate on the first character. Renamed stdarg.h to std_arg.h and endian.h endian_calc.h to avoid name conflicts with /usr/include on some systems that have make utilities that are too smart for their own good. Added additive 55 shuffle generator functions rand(), randbits() and its seed function srand(). Calling rand(a,b) produces a random value over the open half interval [a,b). With one arg, rand(a) is equivalent to rand(0,a). Calling rand() produces 64 random bits and is equivalent to rand(0,2^64). Calling randbit(x>0) produces x random bits. Calling randbit(skip<0) skips -skip bits and returns -skip. The srand() function will return the current state. The call srand(0) returns the initial state. Calling srand(x), where x > 0 will seed the generator to a different state. Calling srand(mat55) (mat55 is a matrix of integers at least 55 elements long) will seed the internal table with the matrix elements mod 2^64. Finally calling srand(state) where state is a generator state also sets/seeds the generator. The cryrand.cal library has been modified to use the builtin rand() number generator. The output of this generator is different from previous versions of this generator because the rand() builtin does not match the additive 55 / shuffle generators from the old cryrand.cal file. Added Makfile support for building BSD/386 releases. The cmp() builtin can now compare complex values. Added the errno() builtin to return the meaning of errno numbers. Added fputc(), fputs(), fgets(), ftell(), fseek() builtins. Added fsize() builtin to determine the size of an open file. Supports systems where file positions and offsets are longer than 2^32 byte, longer than long and/or are not a simple type. When a file file is printed, the file number is also printed: FILE 3 "/etc/motd" (reading, pos 127) Added matsum() to sum all numeric values in a matrix. The following code now works, thanks to a fix by (Ernest Bowen): mat A[3] = {1, 2, 3}; A[0] = A; print A[0]; Also thanks to ernie, calc can process compound expressions such as 1 ? 2 ? 3 : 4 : 5. Also^2 thanks to ernie, the = operator is more general: (a = 3) = 4 (same as a = 3; a = 4) (a += 3) *= 4 (same as a += 3; a *= 4) matfill(B = A, 4) (same as B = A; matfill(B, 4);) Also^3 thanks to ernie, the ++ and -- operators are more general. a = 3 ++(b = a) (a == 3, b == 4) ++++a (a == 5) (++a)++ == 6 (a == 7) (++a) *= b (a == 32, b == 4) Fixed a bug related to calling epsilon(variable) thanks to ernie. Removed trailing whitespace from source and help files. Some compilers do not support the const type. The file have_const.h, which is built from have_const.c will determine if we can or should use const. See the Makefile for details. Some systems do not have uid_t. The file have_uid_t.h, which is built from have_uid_t.c will determine if we can or should depend on uid_t being typefed by the system include files. See the Makefile for details. Some systems do not have memcpy(), memset() and strchr(). The file have_newstr.h, which is built from have_newstr.c will determine if we can or should depend libc providing these functions. See the Makefile for details. The Makefile symbol DONT_HAVE_VSPRINTF is now called HAVE_VSPRINTF. The file have_vs.h, which is built from have_vs.c will determine if we can or should depend libc providing vsprintf(). See the Makefile for details. Removed UID_T and OLD_BSD symbols from the Makefile. A make all of the upper level Makefile will cause the all rule of the lib and help subdirs to be made as well. Fixed bug where reserved keyword used as symbol name caused a core dump. The following are the changes from calc version 2.9.3t7 to 2.9.3t7: The 'show' command by itself will issue an error message that will remind one of the possible show arguments. (thanks to Ha S. Lam ) Fixed an ANSI-C related problem with the use of stringindex() by the show command. ANSI-C interprets "bar\0foo..." as if it were "bar\017oo...". Added a cd command to change the current directory. (thanks to Ha S. Lam ) Calc will not output the initial version string, startup message and command prompt if stdin is not a tty. Thus the shell command: echo "fact(100)" | calc only prints the result. (thanks to Ha S. Lam ) The zmath.h macro zisbig() macro was replaced with zlt16b(), zge24b(), zge31b(), zge32b() and zgtmaxfull() which are independent of word size. The 'too large' limit for factorial operations (e.g., fact, pfact, lcmfact, perm and comb) is now 2^24. Previously it depended on the word size which in the case of 64 bit systems was way too large. The 'too large' limit for exponentiation, bit position (isset, digit, ), matrix operations (size, index, creation), scaling, shifting, rounding and computing a Fibonacci number is 2^31. For example, one cannot raise a number by a power >= 2^31. One cannot test for a bit position >= 2^31. One cannot round a value to 2^31 decimal digit places. One cannot compute the Fibonacci number F(2^31). Andy Fingerhut (thanks!) supplied a fix to a subtle bug in the code generation routines. The basic problem was that addop() is sometimes used to add a label to the opcode table of a function. The addop() function did some optimization tricks, and if one of these labels happens to be an opcode that triggers optimization, incorrect opcodes were generated. Added utoz(), ztou() to zmath.c, and utoq(), qtou() to qmath.c in preparation for 2.9.3t9 mods. The following are the changes from calc version 2.9.2 to 2.9.3t7: Calc can now compile on OSF/1, SGI and IBM RS6000 systems. A number of systems that have both and do not correctly implement both types. On some System V, MIPS and DEC systems, vsprintf() and do not mix. While calc will pass the regression test, use of undefined variables will cause problems. The Makefile has been modified to look for this problem and work around it. Added randmprime.cal which find a prime of the form h*2^n-1 >= 2^x for some given x. The initial search points for 'h' and 'n' are selected by a cryptographic pseudo-random generator. The library script nextprim.cal is now a link to nextprime.cal. The lib/Makefile will take care of this link and install. The show command now takes singular forms. For example, the command 'show builtin' does the same as 'show builtins'. This allows show to match the historic singular names used in the help system. Synced 'show builtin' output with 'help builtin' output. Fixed the ilog2() builtin. Previously ilog2(2^-20) returned -21 instead of -20. The internal function qprecision() has been fixed. The changes ensure that for any e for which 0 < e <= 1: 1/4 < sup(abs(appr(x,e) - x))/e <= 1/2. Here 'sup' denotes the least upper bound over values of x (supremum). Previously calc did: 1/4 <= sup(abs(appr(x,e) - x))/e < 1. Certain 64 bit processors such as the Alpha are now supported. Added -once to the READ command. The command: read -once filename like the regular READ expect that it will ignore filename if is has been previously read. Improved the makefile. One now can select the compiler type. The make dependency lines are now simple foo.o: bar.h lines. While this makes for a longer list, it is easier to maintain and will make future Makefile patches smaller. Added special options for gcc version 1 & 2, and for cc on RS6000 systems. Calc compiles cleanly under the watchful eye of gcc version 2.4.5 with the exception of warnings about 'aggregate has a partly bracketed initializer'. (gcc v2 should allow you to disable this type of warning with using -Wall) Fixed a longjmp bug that clobbered a local variable in main(). Fixed a number of cases where local variables or malloced storage was being used before being set. Fixed a number of fence post errors resulting in reads or writes just outside of malloced storage. A certain parallel processor optimizer would give up on code in cases where math_error() was called. The obscure work-a-rounds involved initializing or making static, certain local variables. The cryrand.cal library has been improved. Due to the way the initial quadratic residues are selected, the random numbers produced differ from previous versions. The printing of a leading '~' on rounded values is now a config option. By default, tilde is still printed. See help/config for details. The builtin function base() may be used to set the output mode or base. Calling base(16) is a convenient shorthand for typing config("mode","hex"). See help/builtin. The printing of a leading tab is now a config option. This does not alter the format of functions such as print or printf. By default, a tab is printed. See help/config for details. The value atan2(0,0) now returns 0 value in conformance with the 4.3BSD ANSI/IEEE 754-1985 math library. For all values of x, x^0 yields 1. The major change here is that 0^0 yields 1 instead of an error. Fixed gcd() bug that caused gcd(2,3,1/2) to ignore the 1/2 arg. Fixed ltol() rounding so that exact results are returned, similar to the way sqrt() and hypot() round, when they exist. Fixed a bug involving ilog2(). Fixed quomod(a,b,c,d) to give correct value for d when a is between 0 and -b. Fixed hmean() to perform the necessary multiplication by the number of arguments. The file help/full is now being built. The man page is not installed by default. One may install either the man page source or the cat (formatted man) page. See the Makefile for details. Added a quit binding. The file lib/bindings2 shows how this new binding may be used. One can now do a 'make check' to run the calc regression test within in the source tree. The regression test code is now more extensive. Updated the help/todo list. A BUGS file was added. Volunteers are welcome to send in patches! The following are the changes from calc version 2.9.1 to 2.9.1: Fixed floor() for values -1 < x < 0. Fixed ceil() for values -1 < x < 0. Fixed frac() for values < 0 so that int(x) + frac(x) == x. Fixed wild fetch bug in zdiv, zquo and zmod code. Fixed bug which caused regression test #719 to fail on some machines. Added more regression test code. The following are the changes from calc version 2.9.0 to 2.9.0: A major bug was fixed in subtracting two numbers when the first number was zero. The problem caused wrong answers and core dumps. The following are the changes from calc version 1.27.0 to 2.8.0: Full prototypes have been provided for all C functions, and are used if calc is compiled with an ANSI compiler. Newly defined variables are now initialized to the value of zero instead of to the null value. The elements of new objects are also initialized to the value of zero instead of null. The gcd, lcm, and ismult functions now work for fractional values. A major bug in the // division for fractions with a negative divisor was fixed. A major bug in the calculation of ln for small values was fixed. A major bug in the calculation of the ln and power functions for complex numbers was fixed. A major lack of precision for sin and tan for small values was fixed. A major lack of precision for complex square roots was fixed. The "static" keyword has been implemented for variables. So permanent variables can be defined to have either file scope or function scope. Initialization of variables during their declaration are now allowed. This is most convenient for the initialization of static variables. The matrix definition statement can now be used within a declaration statement, to immediately define a variable as a matrix. Initializations of the elements of matrices are now allowed. One- dimensional matrices may have implicit bounds when initialization is used. The obj definition statement can now be used within a declaration statement, to immediately define a variable as an object. Object definitions can be repeated as long as they are exactly the same as the previous definition. This allows the rereading of files which happen to define objects. The integer, rational, and complex routines have been made into a 'libcalc.a' library so that they can be used in other programs besides the calculator. The "math.h" include file has been split into three include files: "zmath.h", "qmath.h", and "cmath.h". Following is a list of visible changes to calc from version 1.26.4 to 1.26.4: Added an assoc function to return a new type of value called an association. Such values are indexed by one or more arbitrary values. They are stored in a hash table for quick access. Added a hash() function which accepts one or more values and returns a quickly calculated small non-negative hash value for those values. Following is a list of visible changes to calc from version 1.26.2 to 1.26.4: Misc fixes to Makefiles. Misc lint fixes. Misc portability fixes. Misc typo and working fixes to comments, help files and the man page. Following is a list of visible changes to calc from version 1.24.7 to 1.26.1: There is a new emacs-like command line editing and edit history feature. The old history mechanism has been removed. The key bindings for the new editing commands are slightly configurable since they are read in from an initialization file. This file is usually called /usr/lib/calc/bindings, but can be changed by the CALCBINDINGS environment variable. All editing code is self-contained in the new files hist.c and hist.h, which can be easily extracted and used in other programs. Two new library files have been added: chrem.cal and cryrand.cal. The first of these solves the Chinese remainder problem for a set of modulo's and remainders. The second of these implements several very good random number generators for large numbers. A small bug which allowed division by zero was fixed. A major bug in the mattrans function was fixed. A major bug in the acos function for negative arguments was fixed. A major bug in the strprintf function when objects were being printed was fixed. A small bug in the library file regress.cal was fixed. ## Copyright (C) 2001 Landon Curt Noll ## ## Calc is open software; you can redistribute it and/or modify it under ## the terms of the version 2.1 of the GNU Lesser General Public License ## as published by the Free Software Foundation. ## ## Calc is distributed in the hope that it will be useful, but WITHOUT ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General ## Public License for more details. ## ## A copy of version 2.1 of the GNU Lesser General Public License is ## distributed with calc under the filename COPYING-LGPL. You should have ## received a copy with calc; if not, write to Free Software Foundation, Inc. ## 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ## ## @(#) $Revision: 30.21 $ ## @(#) $Id: CHANGES,v 30.21 2010/09/02 09:50:19 chongo Exp $ ## @(#) $Source: /usr/local/src/cmd/calc/RCS/CHANGES,v $ ## ## Under source code control: 1993/06/02 18:12:57 ## File existed as early as: 1989 ## ## chongo /\oo/\ http://www.isthe.com/chongo/ ## Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ NAME name - return name of some kinds of structure SYNOPSIS name(val) TYPES val any return string or null value DESCRIPTION If val is a named block or open file stream, name(val) returns the name associated with val. Otherwise the null value is returned. Since the name associated with a file stream is that used when the stream was opened, different names may refer to the same file, e.g. "foo" and "./foo". EXAMPLE ; A = blk("alpha"); ; name(A) "alpha" ; f = fopen("/tmp/beta", "w") ; name(f) "/tmp/beta" ; name(files(0)) "(stdin)" LIMITS none LINK LIBRARY none SEE ALSO blk, fopen ## Copyright (C) 1999-2006 Landon Curt Noll ## ## Calc is open software; you can redistribute it and/or modify it under ## the terms of the version 2.1 of the GNU Lesser General Public License ## as published by the Free Software Foundation. ## ## Calc is distributed in the hope that it will be useful, but WITHOUT ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General ## Public License for more details. ## ## A copy of version 2.1 of the GNU Lesser General Public License is ## distributed with calc under the filename COPYING-LGPL. You should have ## received a copy with calc; if not, write to Free Software Foundation, Inc. ## 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ## ## @(#) $Revision: 30.1 $ ## @(#) $Id: name,v 30.1 2007/03/16 11:10:42 chongo Exp $ ## @(#) $Source: /usr/local/src/cmd/calc/help/RCS/name,v $ ## ## Under source code control: 1997/04/05 14:12:44 ## File existed as early as: 1997 ## ## chongo /\oo/\ http://www.isthe.com/chongo/ ## Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ NAME acsch - inverse hyperbolic cosecant SYNOPSIS acsch(x [,eps]) TYPES x nonzero real eps nonzero real, defaults to epsilon() return real DESCRIPTION Returns the acsch of x to a multiple of eps with error less in absolute value than .75 * eps. acsch(x) is the real number v for which csch(v) = x. It is given by acsch(x) = ln((1 + sqrt(1 + x^2))/x) EXAMPLE ; print acsch(2, 1e-5), acsch(2, 1e-10), acsch(2, 1e-15), acsch(2, 1e-20) .48121 .4812118251 .481211825059603 .4812118250596034475 LIMITS none LINK LIBRARY NUMBER *qacsch(NUMBER *x, NUMBER *eps) SEE ALSO asinh, acosh, atanh, asech, acoth, epsilon ## Copyright (C) 1999 Landon Curt Noll ## ## Calc is open software; you can redistribute it and/or modify it under ## the terms of the version 2.1 of the GNU Lesser General Public License ## as published by the Free Software Foundation. ## ## Calc is distributed in the hope that it will be useful, but WITHOUT ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General ## Public License for more details. ## ## A copy of version 2.1 of the GNU Lesser General Public License is ## distributed with calc under the filename COPYING-LGPL. You should have ## received a copy with calc; if not, write to Free Software Foundation, Inc. ## 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ## ## @(#) $Revision: 30.1 $ ## @(#) $Id: acsch,v 30.1 2007/03/16 11:10:42 chongo Exp $ ## @(#) $Source: /usr/local/src/cmd/calc/help/RCS/acsch,v $ ## ## Under source code control: 1995/11/13 03:49:01 ## File existed as early as: 1995 ## ## chongo /\oo/\ http://www.isthe.com/chongo/ ## Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ NAME strcat - concatenate null-terminated strings SYNOPSIS strcat(x1, x2, ...) TYPES x1, x2, ... strings return string DESCRIPTION strcat(x1, x2, ...) forms a string starting with a copy of x1 before the first, if any, null character in x1, followed by the initial non-null characters of any later arguments x2, ... The length of the resulting string will be the sum of the lengths of the component strings considered as null-terminated strings (i.e. the lengths as returned by strlen()). The sum function may be used to concatenate strings where '\0' is to be considered as an ordinary character, either by sum(x1, x2, ...) or sum(list(x1, x2, ...)); in this case, the size of the resulting string is the sum of the sizes of the component strings. EXAMPLE ; A = "abc"; B = "XY"; C = " "; ; print strcat(A, B, C, B, A) abcXY XYabc LIMITS The number of arguments may not to exceed 1024. LINK LIBRARY none SEE ALSO strcmp, strcpy, strerror, strlen, strncmp, strncpy, strpos, strprintf, strscan, strscanf, substr ## Copyright (C) 1999-2006 Landon Curt Noll ## ## Calc is open software; you can redistribute it and/or modify it under ## the terms of the version 2.1 of the GNU Lesser General Public License ## as published by the Free Software Foundation. ## ## Calc is distributed in the hope that it will be useful, but WITHOUT ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General ## Public License for more details. ## ## A copy of version 2.1 of the GNU Lesser General Public License is ## distributed with calc under the filename COPYING-LGPL. You should have ## received a copy with calc; if not, write to Free Software Foundation, Inc. ## 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ## ## @(#) $Revision: 30.1 $ ## @(#) $Id: strcat,v 30.1 2007/03/16 11:10:42 chongo Exp $ ## @(#) $Source: /usr/local/src/cmd/calc/help/RCS/strcat,v $ ## ## Under source code control: 1995/10/05 04:52:27 ## File existed as early as: 1995 ## ## chongo /\oo/\ http://www.isthe.com/chongo/ ## Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ NAME num - numerator of a real number SYNOPSIS num(x) TYPES x real return integer DESCRIPTION For real x, den(x) returns the denominator of x. In calc, real values are actually rational values. Each calc real value can be uniquely expressed as: n / d where: n and d are integers gcd(n,d) == 1 d > 0 If x = n/x, then den(x) == n. EXAMPLE ; print num(7), num(-1.25), num(121/33) 7 -5 11 LIMITS none LINK LIBRARY NUMBER *qnum(NUMBER *x) SEE ALSO den ## Copyright (C) 1999 Landon Curt Noll ## ## Calc is open software; you can redistribute it and/or modify it under ## the terms of the version 2.1 of the GNU Lesser General Public License ## as published by the Free Software Foundation. ## ## Calc is distributed in the hope that it will be useful, but WITHOUT ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General ## Public License for more details. ## ## A copy of version 2.1 of the GNU Lesser General Public License is ## distributed with calc under the filename COPYING-LGPL. You should have ## received a copy with calc; if not, write to Free Software Foundation, Inc. ## 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ## ## @(#) $Revision: 30.1 $ ## @(#) $Id: num,v 30.1 2007/03/16 11:10:42 chongo Exp $ ## @(#) $Source: /usr/local/src/cmd/calc/help/RCS/num,v $ ## ## Under source code control: 1995/10/05 04:52:27 ## File existed as early as: 1995 ## ## chongo /\oo/\ http://www.isthe.com/chongo/ ## Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ digit srandom fgetfile binding  dereference blk helprandomissimple pifreopenstrcmp ceilrcmulhighbitisstr fremsavevalfscan pmod pushctimeptest  cos! asec" sqrt# mne$ list%history&ferror'isptr( cmp)memsize*fseek+asinh, ssq-overview. COPYING-LGPL/ minv0randbit1islist2 abs3resource4 frac5fsize6fputs7wishlist8places9assoc:credit;delete< errorcodes=isconfig> sgn? mod@popcntA objB cpC lcmD scanEerrmaxFcommandGappendHsegmentIfilesJ fullKftellL rmMpowerNAME digit - digit at specified position in a "decimal" representation SYNOPSIS digit(x, n [, b]) TYPES x real n integer b integer >= 2, default = 10 return integer DESCRIPTION d(x,n,b) returns the digit with index n in a standard base-b "decimal" representation of x, which may be described as follows: For an arbitrary base b >= 2, following the pattern of decimal (base 10) notation in elementary arithmetic, a base-b "decimal" representation of a positive real number may be considered to be specified by a finite or infinite sequence of "digits" with possibly a "decimal" point to indicate where the fractional part of the representation begins. Just as the digits for base 10 are the integers 0, 1, 2, ..., 9, the digits for a base-b representation are the integers d for which 0 <= d < b. The index for a digit position is the count, positively to the left, of the number from the "units" position immediately to the left of the "decimal" point; the digit d_n at position n contributes additively d_n * b^n to the value of x. For example, ; d_2 d_1 d_0 . d_-1 d_-2 represents the number ; d_2 * b^2 + d_1 * b + d0 + d_-1 * b^-1 + d_-2 * b^-2 The sequence of digits has to be infinite if den(x) has a prime factor which is not a factor of the base b. In cases where the representation may terminate, the digits are considered to continue with an infinite string of zeros rather than the other possibility of an infinite sequence of (b - 1)s. Thus, for the above example, d_n = 0 for n = -3, -4, ... Similarly, a representation may be considered to continue with an infinite string of zeros on the left, so that in the above example d_n = 0 also for n >= 3. For negative x, digit(x,n,b) is given by digit(abs(x),n,b); the standard "decimal" representation of this x is a - sign followed by the representation of abs(x). In calc, the "real" numbers are all rational and for these the digits following the decimal point eventually form a recurring sequence. With base-b digits for x as explained above, the integer whose base-b representation is ; b_n+k-1 b_n_k-2 ... b_n, i.e. the k digits with last digit b_n, is given by ; digit(b^-r * x, q, b^k) if r and q satisfy n = q * b + r. EXAMPLE ; a = 123456.789 ; for (n = 6; n >= -6; n++) print digit(a, n),; print 0 1 2 3 4 5 6 7 8 9 0 0 0 ; for (n = 6; n >= -6; n--) print digit(a, n, 100),; print 0 0 0 0 12 34 56 78 90 0 0 0 0 ; for (n = 6; n >= -6; n--) print digit(a, n, 256),; print 0 0 0 0 1 226 64 201 251 231 108 139 67 ; for (n = 1; n >= -12; n++) print digit(10/7, n),; print ; 0 1 4 2 8 5 7 1 4 2 8 5 7 1 ; print digit(10/7, -7e1000, 1e6) 428571 LIMITS The absolute value of the integral part of x is assumed to be less than 2^2^31, ensuring that digit(x, n, b) will be zero if n >= 2^31. The size of negative n is limited only by the capacity of the computer being used. LINK LIBRARY NUMBER * qdigit(NUMBER *q, ZVALUE dpos, ZVALUE base) SEE ALSO bit ## Copyright (C) 1999-2006 Landon Curt Noll ## ## Calc is open software; you can redistribute it and/or modify it under ## the terms of the version 2.1 of the GNU Lesser General Public License ## as published by the Free Software Foundation. ## ## Calc is distributed in the hope that it will be useful, but WITHOUT ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General ## Public License for more details. ## ## A copy of version 2.1 of the GNU Lesser General Public License is ## distributed with calc under the filename COPYING-LGPL. You should have ## received a copy with calc; if not, write to Free Software Foundation, Inc. ## 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ## ## @(#) $Revision: 30.1 $ ## @(#) $Id: digit,v 30.1 2007/03/16 11:10:42 chongo Exp $ ## @(#) $Source: /usr/local/src/cmd/calc/help/RCS/digit,v $ ## ## Under source code control: 1995/10/03 10:40:01 ## File existed as early as: 1995 ## ## chongo /\oo/\ http://www.isthe.com/chongo/ ## Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ NAME srandom - seed the Blum-Blum-Shub pseudo-random number generator SYNOPSIS srandom([state]) srandom(seed) srandom(seed, newn) srandom(seed, ip, iq, trials) TYPES state random state seed integer newn integer ip integer iq integer trails integer return random state DESCRIPTION Seed the pseudo-random number using the Blum-Blum-Shub generator. There are two primary values contained inside generator state: Blum modulus: A product of two primes. Each prime is 3 mod 4. Quadratic residue: Some integer squared modulo the Blum modulus. Seeding the generator involves changing the Quadratic residue and in most cases the Blum modulus as well. In addition to the two primary values values, an internal buffer of unused random output is kept. When the generator is seeded, any buffered random output is tossed. In each of the following cases, srandom returns the previous state of the generator. Depending on what args are supplied, a new generator state is established. The exception is the no-arg state. 0 args: srandom() Returns the current generator state. Unlike all of the other srandom calls, this call does not modify the generator, nor does it flush the internal bits. 1 arg (state arg): srandom(state) sets the generator to 'state', where 'state' is a previous return of srandom(). 1 arg (0 seed): srandom(0) Sets the generator to the initial startup state. This a call of srandom(0) will restore the generator to the state found when calc starts. 1 arg (seed >= 2^32): srandom(21609139158123209^9+17) The seed value is used to compute the new quadratic residue. The seed passed will be successively squared mod the Blum modulus until we get a smaller value (modulus wrap). The calc resource file produces an equivalent effect: /* assume n is the current Blum modulus */ r = seed; do { last_r = r; r = pmod(r, 2, n); } while (r > last_r); /* r is the new Quadratic residue */ In this form of srandom, the Blum modulus is not changed. NOTE: [1,2^32) seed values and seed<0 values are reserved for future use. 2 args (seed, newn>=2^32): srandom(seed, newn) The newn value is used as the new Blum modulus. This modulus is assumed to be a product of two primes that are both 3 mod 4. The newn value is not factored, it is only checked to see if it is 1 mod 4. In this call form, newn value must be >= 2^32. The seed arg is used to establish the initial quadratic value once newn has been made the Blum moduli. The seed must be either 0 or >= 2^32. If seed == 0, the initial quadratic residue used with srandom(0) is used with the new Blum moduli. If seed >= 2^32, then srandom(seed, newn) has the same effect as: srandom(0, newn); /* set Blum modulus & def quad res */ srandom(seed); /* set quadratic residue */ Use of newn values that are not the product of two 3 mod 4 primes will result in a non-cryptographically strong generator. While the generator will produce values, their quality will be suspect. The period of the generator determines how many bits will be produced before it repeats. The period is determined by the Blum modulus. Some newn values (that are a product of two 3 mod 4 primes) can produce a generator with a very short period making is useless for most applications. When Blum modulus is p*q, the period of a generator is: lcm(factors of p-1 and q-1) One can construct a generator with a maximal period when 'p' and 'q' have the fewest possible factors in common. The quickest way to select such primes is only use 'p' and 'q' when '(p-1)/2' and '(q-1)/2' are both primes. Assuming that fp=(p-1)/2, fq=(q-1)/2, p and q are all primes 3 mod 4, the period of the generator is the longest possible: lcm(factors of p-1 and q-1) == lcm(2,fp,2,fq) = 2*fp*fq = ~n/2 The following calc resource file: /* find first Blum prime: p */ fp = int((ip-1)/2); do { do { fp = nextcand(fp+2, 1, 0, 3, 4); p = 2*fp+1; } while (ptest(p, 1, 0) == 0); } while (ptest(p, trials) == 0 || ptest(fp, trials)); /* find second Blum prime: q */ fq = int((iq-1)/2); do { do { fq = nextcand(fq+2, 1, 0, 3, 4); q = 2*fq+1; } while (ptest(q, 1, 0) == 0); } while (ptest(q, trials) == 0 || ptest(fq, trials)); /* seed the generator */ srandom(ir, p*q); Where: ip initial search location for the Blum prime 'p' iq initial search location for the Blum prime 'q' ir initial Blum quadratic residue generator. The 'ir' must be 0 or >= 2^32, preferably large some random value < p*q. The following may be useful to set ir: srand(p+q); ir = randbit(highbit(p)+highbit(q)) trials number of pseudo prime tests that a candidate must pass before being considered a probable prime (must be >0, try 25) The calc standard resource file seedrandom.cal will produce a seed a generator. If the config value custom("resource_debug") is 0 or 1, then the selected Blum modulus and quadratic residue will be printed. If the global value is 1, then p and q are also printed. The resource file defines the function: seedrandom(seed1, seed2, size [, trials]) Where: seed1 A random number >= 10^20 and perhaps < 10^93. seed2 A random number >= 10^20 and perhaps < 10^93. size Minimal Blum modulus size in bits, This must be >= 32. A value of 512 might be a good choice. trials number of pseudo prime tests that a candidate must pass before being considered a probable prime (must be >0, try 25). Using the default value of 25 might be a good choice. Unfortunately finding optimal values can be very slow for large values of 'p' and 'q'. On a 200Mhz r4k, it can take as long as 1 minute at 512 bits, and 5 minutes at 1024 bits. For the sake of speed, you may want to use to use one of the pre-compiled in Blum moduli via the [1 If you don't want to use a pre-compiled in Blum moduli you can compute your own values ahead of time. This can be done by a method of your own choosing, or by using the seedrandom.cal resource file in the following way: 1) calc # run calc 2) read seedrandom # load seedrandom 3) config("resource_debug",0) # we want the modulus & quad res only 4) seedrandom( ~pound out 20-93 random digits on the keyboard~, ~pound out 20-93 random digits on the keyboard~, 512 ) 5) save the seed and newn values for later use NOTE: [1,2^32) seed values, seed<0 values, [21,2^32) newn values and newn<=0 values are reserved for future use. 2 args (seed, 1>=newn>=20): srandom(seed, newn) The newn is used to select one of 20 pre-computed Blum moduli. The seed arg is used to establish the initial quadratic value once newn has been made the Blum moduli. The seed must be either 0 or >= 2^32. If seed == 0, the pre-compiled quadratic residue for the given newn is selected. If seed >= 2^32, then srandom(seed, newn) has the same effect as: srandom(0, newn); /* set Blum modulus & def quad res */ srandom(seed); /* set quadratic residue */ Note that unlike the newn>=2^32 case, a seed if 0 uses the pre-compiled quadratic residue for the selected pre-compiled Blum moduli. The pre-defined Blum moduli and quadratic residues were selected by LavaRnd, a hardware random number generator. See the URL: http://www.LavaRnd.org/ for an explanation of how the LavaRnd random number generator works. For more information, see the comments at the top of the calc source file, zrandom.c. The purpose of these pre-defined Blum moduli is to provide users with an easy way to use a generator where the individual Blum primes used are not well known. True, these values are in some way "MAGIC", on the other hand that is their purpose! If this bothers you, don't use them. The value 'newn' determines which pre-defined generator is used. newn == 1: (Blum modulus bit length 130) newn == 2: (Blum modulus bit length 137) newn == 3: (Blum modulus bit length 147) newn == 4: (Blum modulus bit length 157) newn == 5: (Blum modulus bit length 257) newn == 6: (Blum modulus bit length 259) newn == 7: (Blum modulus bit length 286) newn == 8: (Blum modulus bit length 294) newn == 9: (Blum modulus bit length 533) newn == 10: (Blum modulus bit length 537) newn == 11: (Blum modulus bit length 542) newn == 12: (Blum modulus bit length 549) newn == 13: (Blum modulus bit length 1048) newn == 14: (Blum modulus bit length 1054) newn == 15: (Blum modulus bit length 1055) newn == 16: (Blum modulus bit length 1062) newn == 17: (Blum modulus bit length 2062) newn == 18: (Blum modulus bit length 2074) newn == 19: (Blum modulus bit length 2133) newn == 20: (Blum modulus bit length 2166) See the comments near the top of the source file, zrandom.c, for the actual pre-compiled values. The Blum moduli associated with 1 <= newn < 9 are subject to having their Blum moduli factored, depending in their size, by small PCs in a reasonable to large supercomputers/highly parallel processors over a long time. Their value lies in their speed relative the the default Blum generator. As of Feb 1997, the Blum moduli associated with 13 <= newn < 20 appear to be well beyond the scope of hardware and algorithms, and 9 <= newn < 12 might be factorable with extreme difficulty. The following table may be useful as a guide for how easy it is to factor the modulus: 1 <= newn <= 4 PC using ECM in a short amount of time 5 <= newn <= 8 Workstation using MPQS in a short amount of time 8 <= newn <= 12 High end supercomputer or high parallel processor using state of the art factoring over a long time 12 <= newn <= 16 Beyond Feb 1997 systems and factoring methods 17 <= newn <= 20 Well beyond Feb 1997 systems and factoring methods In other words, use of newn == 9, 10, 11 and 12 is likely to work just fine for all but the truly paranoid. NOTE: [1,2^32) seed values, seed<0 values, [21,2^32) newn values and newn<=0 values are reserved for future use. 4 args (seed, ip>=2^16, iq>=2^16, trials): srandom(seed, ip, iq, 25) The 'ip' and 'iq' args are used to find simples prime 3 mod 4 The call srandom(seed, ip, iq, trials) has the same effect as: srandom(seed, nextcand(ip, trials,0, 3,4)*nextcand(iq, trials,0, 3,4)); Note that while the newn is very likely to be a product of two primes both 3 mod 4, there is no guarantee that the period of the generator will be long. The likelihood is that the period will be long, however. See one of the 2 arg srandom calls above for more information on this issue. NOTE: [1,2^32) seed values, seed<0 values, [21,2^32) newn values, newn<=0 values, ip<2^16 and iq<2^16 are reserved for future use. See the random help file for details on the generator. EXAMPLE ; srandom(0x8d2dcb2bed3212844f4ad31) RANDOM state ; state = srandom(); ; print random(123), random(123), random(123), random(123), random(123) 42 58 57 82 15 ; print random(123), random(123), random(123), random(123), random(123) 90 121 109 114 80 ; state2 = srandom(state); ; print random(123), random(123), random(123), random(123), random(123) 42 58 57 82 15 ; print random(123), random(123), random(123), random(123), random(123) 90 121 109 114 80 ; state3 = srandom(); ; print state3 == state2; 1 ; print random(); 2101582493746841221 LIMITS integer seed == 0 or >= 2^32 for newn >= 2^32: newn % 4 == 1 for small newn: 1 <= newn <= 20 ip >= 2^16 iq >= 2^16 LINK LIBRARY RAND *zsrandom(ZVALUE *pseed, MATRIX *pmat55) RAND *zsetrandom(RAND *state) SEE ALSO seed, srand, randbit, isrand, random, srandom, israndom ## Copyright (C) 1999 Landon Curt Noll ## ## Calc is open software; you can redistribute it and/or modify it under ## the terms of the version 2.1 of the GNU Lesser General Public License ## as published by the Free Software Foundation³Ê. ## ## Calc is distributed in the hope that it will be useful, but WITHOUT ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General ## Public License for more details. ## ## A copy of version 2.1 of the GNU Lesser General Public License is ## distributed with calc under the filename COPYING-LGPL. You should have ## received a copy with calc; if not, write to Free Software Foundation, Inc. ## 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ## ## @(#) $Revision: 30.1 $ ## @(#) $Id: srandom,v 30.1 2007/03/16 11:10:42 chongo Exp $ ## @(#) $Source: /usr/local/src/cmd/calc/help/RCS/srandom,v $ ## ## Under source code control: 1997/02/17 01:18:22 ## File existed as early as: 1997 ## ## chongo /\oo/\ http://www.isthe.com/chongo/ ## Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ NAME fgetfile - read the rest of a file to form a string SYNOPSIS fgetfile(fs) TYPES fs file stream open for reading return string or null value DESCRIPTION If the current file position for fs is the end of the file, the null value is returned. Otherwise the function returns the string formed from reading all characters from the current file position to the end of the file. If the content of the file "newfile" is a sequence of statements that could form the body of function definition, the statement sequence fs = fopen("newfile", "r"); eval(fgetfile(fs)); achieves the same as the command read newfile; EXAMPLE ; f = fopen("/tmp/newfile", "w") ; fputs(f, "abc\0xyz\n\t\xb0\0\r\v123" ; freopen(f, "r") ; estr(fgetfile(f)) ""abc\0xyz\n\t\xb0\0\r\v123"" LIMITS none LINK LIBRARY none SEE ALSO fgets, fgetstr, files, fopen, fprintf, fputs, fputstr ## Copyright (C) 1999-2006 Landon Curt Noll ## ## Calc is open software; you can redistribute it and/or modify it under ## the terms of the version 2.1 of the GNU Lesser General Public License ## as published by the Free Software Foundation. ## ## Calc is distributed in the hope that it will be useful, but WITHOUT ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General ## Public License for more details. ## ## A copy of version 2.1 of the GNU Lesser General Public License is ## distributed with calc under the filename COPYING-LGPL. You should have ## received a copy with calc; if not, write to Free Software Foundation, Inc. ## 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ## ## @(#) $Revision: 30.1 $ ## @(#) $Id: fgetfile,v 30.1 2007/03/16 11:10:42 chongo Exp $ ## @(#) $Source: /usr/local/src/cmd/calc/help/RCS/fgetfile,v $ ## ## Under source code control: 1996/04/30 03:05:17 ## File existed as early as: 1996 ## ## chongo /\oo/\ http://www.isthe.com/chongo/ ## Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ # bindings - default key bindings for calc line editing functions # # Copyright (C) 1999 David I. Bell # # Calc is open software; you can redistribute it and/or modify it under # the terms of the version 2.1 of the GNU Lesser General Public License # as published by the Free Software Foundation. # # Calc is distributed in the hope that it will be useful, but WITHOUT # ANY WARRANTY; without even the implied warranty of MERCHANTABILITY # or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General # Public License for more details. # # A copy of version 2.1 of the GNU Lesser General Public License is # distributed with calc under the filename COPYING-LGPL. You should have # received a copy with calc; if not, write to Free Software Foundation, Inc. # 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. # # @(#) $Revision: 30.1 $ # @(#) $Id: bindings,v 30.1 2007/03/16 11:09:54 chongo Exp $ # @(#) $Source: /usr/local/src/cmd/calc/cal/RCS/bindings,v $ # # Under source code control: 1993/05/02 20:09:19 # File existed as early as: 1993 # # Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ # NOTE: This facility is ignored if calc was compiled with GNU-readline. # In that case, the standard readline mechanisms (see readline(3)) # are used in place of those found below. map base-map default insert-char ^@ set-mark ^A start-of-line ^B backward-char ^D delete-char ^E end-of-line ^F forward-char ^H backward-kill-char ^J new-line ^K kill-line ^L refresh-line ^M new-line ^N forward-history ^O save-line ^P backward-history ^R reverse-search ^T swap-chars ^U flush-input ^V quote-char ^W kill-region ^Y yank ^? backward-kill-char ^[ ignore-char esc-map map esc-map default ignore-char base-map G start-of-line H backward-history P forward-history K backward-char M forward-char O end-of-line S delete-char g goto-line s backward-word t forward-word d forward-kill-word u uppercase-word l lowercase-word h list-history ^[ flush-input [ arrow-key NAME * - dereference or indirection operator SYNOPSIS * X TYPES X address or lvalue return any DESCRIPTION When used as a binary operator, '*' performs multiplication. When used as a operator, '*' returns the value at a given address. If X is an address, *X returns the value at that address. This value will be an octet, lvalue, string, or number, depending on the type of address. Thus, for any addressable A, *&A is the same as A. If X is an lvalue, *X returns the current value at the address considered to be specified by X. This value may be an lvalue or octet, in which cases, for most operations except when X is the destination of an assignment, *X will contribute the same as X to the result of the operation. For example, if A and B are lvalues whose current values are numbers, A + B, *A + B, A + *B and *A + *B will all return the same result. However if C is an lvalue and A is the result of the assignment A = &C, then A = B will assign the value of B to A, *A = B will assign the value of B to C without affecting the value of A. If X is an lvalue whose current value is a structure (matrix, object, list, or association), the value returned by *X is a copy of the structure rather than the structure identified by X. For example, suppose B has been created by ; mat B[3] = {1,2,3} then ; A = *B = {4,5,6} will assign the values 4,5,6 to the elements of a copy of B, which will then become the value of A, so that the values of A and B will be different. On the other hand, ; A = B = {4,5,6} will result in A and B having the same value. If X is an octet, *X returns the value of that octet as a number. The * operator may be iterated with suitable sequences of pointer-valued lvalues. For example, after ; global a, b, c; ; b = &a; ; c = &b; **c returns the lvalue a; ***c returns the value of a. EXAMPLE ; mat A[3] = {1,2,3} ; p = &A[0] ; print *p, *(p + 1), *(p + 2) 1 2 3 ; *(p + 1) = 4 ; print A[1] 4 ; A[0] = &a ; a = 7 ; print **p 7 LIMITS none LINK LIBRARY none SEE ALSO address, isptr ## Copyright (C) 1999-2006 Landon Curt Noll ## ## Calc is open software; you can redistribute it and/or modify it under ## the terms of the version 2.1 of the GNU Lesser General Public License ## as published by the Free Software Foundation. ## ## Calc is distributed in the hope that it will be useful, but WITHOUT ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General ## Public License for more details. ## ## A copy of version 2.1 of the GNU Lesser General Public License is ## distributed with calc under the filename COPYING-LGPL. You should have ## received a copy with calc; if not, write to Free Software Foundation, Inc. ## 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. ## ## @(#) $Revision: 30.1 $ ## @(#) $Id: dereference,v 30.1 2007/03/16 11:10:42 chongo Exp $ ## @(#) $Source: /usr/local/src/cmd/calc/help/RCS/dereference,v $ ## ## Under source code control: 1997/09/06 20:03:34 ## File existed as early as: 1997 ## ## chongo /\oo/\ http://www.isthe.com/chongo/ ## Share and enjoy! :-) http://www.isthe.com/chongo/tech/comp/calc/ NAME blk - generate or modify block values SYNOPSIS blk([len, chunk]); blk(val [, len, chunk]); TYPES len null or integer chunk null or integer val non-null string, block, or named block return block or named block DESCRIPTION With only integer arguments, blk(len, chunk) attempts to allocate a block of memory consisting of len octets (unsigned 8-bit bytes). Allocation is always done in multiples of chunk octets, so the actual allocation size of len rounded up to the next multiple of chunk. The default value for len is 0. The default value for chunk is 256. If the allocation is successful, blk(len, chunk) returns a value B, say, for which the octets in the block may be referenced by B[0], B[1], ... , B[len-1], these all initially having zero value. The octets B[i] for i >= len always have zero value. If B[i] with some i >= len is referenced, size(B) is increased to i + 1. For example: B[i] = x has an effect like that of two operations on a file stream fs: fseek(fs, pos); fputc(fs, x). Similarly: x = B[i] is like: fseek(fs, pos); x = fgetc(fs). The value of chunk is stored as the "chunksize" for B. The size(B) builtin returns the current len for the block; sizeof(B) returns its maxsize; memsize(B) returns maxsize + overhead for any block value. Also size(B) is analogous to the length of a file stream in that if size(B) < sizeof(B): B[size(B)] = x will append one octet to B and increment size(B). The builtin test(B) returns 1 or 0 according as at least one octet is nonzero or all octets are zero. If B1 and B2 are blocks, they are considered equal (B1 == B2) if they have the same length and the same data, i.e. B1[i] == B2[i] for 0 <= i < len. Chunksizes and maxsizes are ignored. The output for print B occupies two lines, the first line giving the chunksize, number of octets allocated (len rounded up to the next chunk) and len, and the second line up to 30 octets of data. If the datalen is zero, the second line is blank. If the datalen exceeds 30, this indicated by a trailing "...". If a block value B created by B = blk(len, chunk) is assigned to another variable by C = B, a new block of the same structure as B is created to become the value of C, and the octets in B are copied to this new block. A block with possibly different length or chunksize is created by C = blk(B, newlen, newchunk), only the first min(len, newlen) octets being copied from B; later octets are assigned zero value. If omitted, newlen and newchunk default to the current datalen and chunk-size for B. The current datalen, chunksize and number of allocated octets for B may be changed by: B = blk(B, newlen, newchunk). No data is lost if newlen is greater than or equal to the old size(B). The memory block allocated by blk(len, chunk) is freed at or before termination of the statement in which this occ