allanswers.org - FAQ: BETA Programming Language (version 1.11 - 08 Dec 97)

 Home >  Programming >

FAQ: BETA Programming Language (version 1.11 - 08 Dec 97)

Section 4 of 6 - Prev - Next
All sections - 1 - 2 - 3 - 4 - 5 - 6



   hello1: @Label(##);
   hello2: @Label(##);

or specify the name explicitly instead.
See the X Windows Libraries Manual p5-7 for more details.

----------------------------------------------------------------------------

X02) Why do I get the error "There must be only one non-shell widget which
is son of Toplevel"?

Consider the following program:

   ORIGIN '~beta/Xt/current/awenv';
   --- program: descriptor ---
   AwEnv
   (# faculty: label
        (# init:: (# do 2-> borderwidth #) #);
      University: @box
        (# Physics, Mathematics: @faculty;
           init:: (# do Physics.init; Mathematics.init #);
        #)
   do University.init;
   #)

The idea was that a window with two labels named Physics and Mathematics
should appear. But executing it gives the error message

     Xt Error: There must be only one non-shell widget which is son of
     Toplevel. The widget causing the conflict is named faculty.

This is because the program uses the init pattern of the widgets without
specifying the father and name of the widgets. In the Xt manual [MIA 91-16],
it is briefly explained that the father widget will default to "the
enclosing widget according to BETA's scope rules" (see the description of
Core in "Basic XtEnv patterns").

To be precise, this is what happens: When the init pattern of a widget is
invoked, it first checked to see if the father is NONE. This will be the
case if no father is specified in the enter part of init. If so, a search is
started in the statical environment of the widget pattern. If a
specialization of a Core widget is found, this widget is used as the father.
This search is continued until a pattern with no enclosing pattern is found.
In this case the widget named TopLevel (in xtenv) is used as the father. The
widget TopLevel is an instance of the pattern TopLevelShell, which among its
characteristics has the constraint that it wants to have exactly one
non-shell child.

Now consider the example program: The first thing that happens is that the
init attribute of University is invoked. Since no father is specified, a
search for one is started from the University pattern. This search finds the
pattern AwEnv(# ... #), which is not a Core, and which has no enclosing
pattern. Thus University will get the father widget TopLevel.

The final binding of University.init then invokes Physics.init. Physics is
an instance of the pattern faculty, which is declared in the same scope as
University. Thus the search for a father for Physics is identical to the
search for the father of University, and Physics also gets TopLevel as its
father. This is when the error occurs. The reason why the name reported in
the error message is faculty is explained in Question X01.

Notice that it did not matter that the instantiation of the Physics object
is done within University: the default father is searched for starting from
the pattern declaration of the object.

In general there are three possible solutions:

  1. Supply the father and name when initializing the faculty widgets:

        do ("Physics", University)->Physics.init;
           ("Mathematics", University)->Mathematics.init;

     In this case, no search for a default father is needed for the faculty
     widgets.
  2. Make (possibly empty) specializations of faculty inside University:

        Physics: @faculty(##);
        Mathematics: @faculty(##);

     Now the search for a default father of Physics will start at the
     pattern faculty(##) inside University, so the University pattern will
     be the first found in this search, and hence the University widget will
     become the father of the Physics widget. Likewise for Mathematics.
  3. Move the declaration of the faculty pattern inside the University
     pattern. This will give the same search path as in solution 2.
     (Conceptually, this might also be the best place to declare faculty in
     the first place.)

The above example was a simple one. In more complicated cases, the reason
for an error of this kind can be trickier to spot. If your program uses the
fragment system to move declarations of useful widgets into a library, this
kind of error is likely to occur. Remember that if an instance of an
unspecialized widget is used, the widget pattern being declared in, say, the
XtEnvLib attributes slot of xtenv, then the search for a default father is
started at the XtEnv pattern, and therefore no father widget is found. In
this case the widget will get TopLevel as father. Solutions 1 or 2 above
will be appropriate in these cases.
See the X Windows Libraries Manual p5-7 for more details.

----------------------------------------------------------------------------

X03) How do I get a separate window for my widget?

Widgets that create separate windows which can be individually moved,
resized, and so on, by the window manager are specializations of the Shell
pattern. Normally you would use a TopLevelShell (the pattern used for the
TopLevel widget created by default by XtEnv).

To make the following Athena Label appear in a separate window

   goodbye: @Label(# init:: (# do 'Goodbye World'->label #)

you would wrap a TopLevelShell around it:

   byewindow: @TopLevelShell
     (# goodbye: @Label
          (# init:: (# do 'Goodbye World'->label #) #);
        init:: (# do goodbye.init #);
     #);

To make the window appear, it should be initialized like any other widget,
and then the Shell method popup should be invoked:

   byewindow.init;
   byewindow.popup;

Notice that the first widget initialized by a program will by default become
a child of the TopLevel widget (see question X02), and will thus be in a
separate window.

There are other possible shells to use, such as OverrideShell. The
OverrideShell has gotten its name because although it creates a separate top
level window, it overrides all requests from the window manager, and will
therefore not be resizable, etc.
----------------------------------------------------------------------------

X04) Why do I get the error "clockWidgetClass: undefined" when linking my
AwEnv program using the xt/v1.8 libraries? [corrected in r4.0]

The X libraries in the Mjolner System are based on X11 release 5 (X11R4/R5).
Support for X11R6 is not included in release 3.0 of the Mjolner System. But
with a few exceptions, X11R6 is backward compatible with X11R5. One of the
few exceptions is the reason for the above error: Some very infrequently
used widgets have been removed from the Athena widget set in X11R6.

To fix the error you should have your system administrator apply the
following patch to the file ~beta/Xt/v1.8/private/external/awInt.c:

   13d12
   < #include 
   15,16d13
   < #include 
   < #include 
   37d33
   <
   53,55d48
   < int getClockWidgetClass(){return ( (long) clockWidgetClass);}
   < int getLogoWidgetClass(){return ( (long) logoWidgetClass);}
   < int getMailboxWidgetClass(){return ( (long) mailboxWidgetClass);}

That is, remove all lines referring to the clock, logo, and mailbox widgets.
Then the system administrator should compile one of the awenv demos to get
the changes incorporated into the system.

To simplify correction of the above errors, a patch for the Mjolner System,
release 3.0 and 3.1 has been supplied. It can be fetched from
ftp://ftp.mjolner.com/pub/X11R6_patch,`.

Please see the README file for details.
----------------------------------------------------------------------------

X05) Why do I get the error "Error: NULL ArgVal in XtGetValues" when
executing my Xt program using the xt/v1.8 libraries? [corrected in r4.0]

This is due to a programming error in the Mjolner System interface to the X
toolkit. The error does not seem to influence programs linked under X11
release 5, but (at least) X11R6 on Linux encounters it.

To fix the error have your system administrator change some files:

  1. In the file ~beta/Xt/v1.8/xtlib.bet, the definition of the pattern
     argList should be changed to:

     argList: cStruct
       (# byteSize::< (# do 100->value #);
          max: (# exit R.range div 2 #);
          extend:
            (# size: @integer;
            enter size
            do (if size=0 then R.range->size
                else size-R.range->size;
               if);
               size->R.extend;
            #);
          set: @
            (# number: @integer;
               cStr: @integer;
               value: @integer;
            enter (number,cstr,value)
            do (* Cannot check ranges since no GC's may occur.
                * The user needs to do the bookkeeping himself
                * using 'max' and 'extend'.
                * The reason for this is that 'value' may be
                * the computed address of an integer.
                *)
               cstr->R[number*2-1];
               value->R[number*2]
            #);
          get: @
            (# number: @integer;
            enter number
            exit R[number*2]
            #);
          getName: @
            (# number: @integer;
               t: ^text;
            enter number
            do r[2*number-1]->CStringToText->t[];
            exit t[]
            #);
       #);

  2. In the file ~beta/Xt/v1.8/private/xtenvbody.bet, the two fragments
     IntegerResourceGet and AncestorSensitiveGet should be changed to:

        --- IntegerResourceGet: dopart ---
        do (1,resourceName, @@value)->private.wargs.set;
           (Thewidget,private.wargs[],1)->XtGetValues;

     and

        --- AncestorSensitiveGet: dopart ---
        do (1,xtnancestorsensitive,@@value)->private.wargs.set;
           (Thewidget,private.wargs[],1)->XtGetValues;

     respectively.
  3. In the file ~beta/Xt/v1.8/private/awenvbody.bet, the fragment
     FloatResourceGet should be changed to:

        --- FloatResourceGet: descriptor ---
        (# status,res: @integer
        do (1,resourceName,@@value)->private.wargs.set;
           (theWidget,private.wargs[],1)->XtGetValues;
           resolution->res;
           (@@value,res)->getQuotFromFloat->value
        #)

  4. In the file ~beta/Xt/v1.8/motif/private/basicsbody.bet, the three
     fragments MotifStringResourceGetText, MotifStringResourceGet, and
     ProcResourceGet should be changed to:

        --- MotifStringResourceGetText: descriptor ---
        (# S: @MotifString;
        do (1,resourceName,@@S.value)->Private.Wargs.Set;
           (TheWidget,Private.Wargs[],1)->XtGetValues;
           S.getText->t[];
           S.destroy;
        #)

     and

        --- MotifStringResourceGet: descriptor ---
        (#
        do (1,resourceName,@@value)->private.wargs.set;
           (thewidget,private.wargs[],1)->XtGetValues;
        #)

     and

        --- ProcResourceGet: descriptor ---
        (#
        do (1,resourceName,@@p)->private.wargs.set;
           (Thewidget,private.wargs[],1)->XtGetValues;
        #)

     respectively.
  5. In the file ~beta/Xt/v1.8/motif/private/rowcolumnbody.bet the two
     fragments RowColumnLabelStringGetText and RowColumnLabelStringGet
     should be changed to:

        --- RowColumnLabelStringGetText: descriptor ---
        (# S: @MotifString;
        do (1,resourceName,@@S.value)->Private.Wargs.Set;
           (TheWidget,Private.Wargs[],1)->XtGetValues;
           S.getText->t[];
           S.destroy;
        #)

     and

        --- RowColumnLabelStringGet: descriptor ---
        (#
        do (1,resourceName,@@value)->private.wargs.set;
           (thewidget,private.wargs[],1)->XtGetValues;
        #)

     respectively.
  6. Then have your system administrator issue the commands

        cd $BETALIB/Xt/v1.8
        beta -q -c private/awenvbody.bet motif/private/rowcolumnbody.bet

     to get the changed files recompiled.

These changes will be incorporated in version 1.9 of the Xt libraries.

To simplify correction of the above errors, a patch for the Mjolner System,
release 3.0 and 3.1 has been supplied. It can be fetched from
ftp://ftp.mjolner.com/pub/X11R6_patch,`.

Please see the README file for details.
----------------------------------------------------------------------------

X06) How do I set font information in MotifStrings?

In order to set font information in MotifStrings, you can use the following
as a template:

   sensorLabel: @Label
     (# init::
          (# s: @labelString;
             t: @MotifString
                  (# init::
                       (#
                       do ('Sensor:','ItalFont',XmSTRING_DIRECTION_L_TO_R)
                            -> t.setTextSegment;
                       #);
                  #);
          do (...)
             t.init;
             t->s.set;
          #);
     #);

----------------------------------------------------------------------------

X07) Resource specification errors in Xt/v1.9 [corrected in r4.0]

Version 1.9 of the BETA interface to X (part of r4.0) solves most of the
errors appearing when using X11R6 (e.g. the errors in X04 and X05).

This is done, among other things, by introducing BooleanResource,
CharResource and ShortResource to correctly model the interface to X
resources with different physical representations.

Unfortunately a few of the resources was not converted correctly. This means
that you may get wrong behaviour when reading these resources.

To fix this you can change the following in the Xt/v1.9 sources, and
recompile the libraries (after appropriate setting of permissions):

   Change from IntegerResource to ShortResource:
   ---------------------------------------------
   motif/rowcolumn.bet:         RowColumn.numColumns
   motif/texts.bet:             TextField.columns

   Change from IntegerResource to BooleanResource:
   -----------------------------------------------
   awenv.bet:                   SimpleMenu.menuOnScreen
   awenv.bet:                   Paned.refigureMode
   awenv.bet:                   AsciiText.autoFill
   awenv.bet:                   AsciiText.resize
   awenv.bet:                   AsciiText.displayNonprinting
   awenv.bet:                   CoreLIB.resizable
   xtenv.bet:                   Core.mappedWhenManaged
   xtenv.bet:                   Shell.allowShellResize
   xtenv.bet:                   Shell.overrideRedirect
   xtenv.bet:                   Shell.saveUnder
   xtenv.bet:                   WMShell.input
   xtenv.bet:                   WMShell.transient
   xtenv.bet:                   WMShell.waitForWM
   xtenv.bet:                   TopLevelShell.iconic
   motif/bulletinboard.bet:     BulletinBoard.defaultPosition
   motif/lists.bet:             MotifList.automaticSelection
   motif/scale.bet:             Scale.highlightOnEnter
   motif/texts.bet:             ScrolledText.scrollVertical
   motif/texts.bet:             ScrolledText.scrollHorizontal
   motif/texts.bet:             ScrolledText.scrollLeftSide
   motif/texts.bet:             ScrolledText.scrollTopSide
   motif/texts.bet:             TextField.verifyBell

These errors will naturally be corrected in the next release.
----------------------------------------------------------------------------

SECTION III: The BETA compiler

----------------------------------------------------------------------------

C01) What is the execution speed of BETA programs?

For average programs, the execution speed of typical BETA programs is
comfortable. However, there are many possibilities for optimization in the
current BETA compiler, the generated code, and the run-time system. Mjolner
Informatics is constantly working on improving the execution speed of BETA.
----------------------------------------------------------------------------

C02) How do I get rid of the warning: "A run-time qualification check will
be inserted here"?

By using the -q or -w options to the compiler: "beta -q ..." or "beta -w
..."
----------------------------------------------------------------------------

C03) What *does* that Qua-check warning mean, anyway?

If you have:

   (# Vehicle: (# ... #);
      Bus: Vehicle(# ... #);
      aVehicle: ^Vehicle;
      aBus: ^Bus
   do ...
      aVehicle[]->aBus[]
      ...
   #)

the compiler will give a Qua-check warning at the "aVehicle[]->aBus[]". The
reason is that aBus can only refer to objects which are instances of a
pattern that is a subpattern of Bus (or is a Bus). But aVehicle may refer to
all objects which are instances of a pattern that is a subpattern of Vehicle
(or is a Vehicle) - that is, not necessarily Bus. The BETA runtime system
therefore inserts a test to verify that the object referenced by aVehicle[]
is actually an instance of a pattern that is a subpattern of Bus (or is a
Bus) - otherwise a runtime error occurs.

The Qua-warning is issued to direct your attention towards these places for
potential runtime errors.
----------------------------------------------------------------------------

C04) How do I work around "*****Repetition of non simple patterns is not
implemented" (using v5.0 of the compiler)? [corrected in r4.0]

If you want to write:

   persons: [100]@person

(which is not implemented in version 5.0 of the BETA compiler), you should
instead write:

   persons: [100]^persons

and then, before you start using the persons repetition, initialize it by:

   (for i: persons.range repeat
        &person[]->persons[i][]
   for)

Then you can use the persons repetition in the rest of the program, just as
if it was declared as a repetition of static persons.

In version 5.1 of the BETA compiler, persons: [100]@person is implemented.
----------------------------------------------------------------------------

C05) How do I work around "Labeled imperative not implemented"?

If you want to write:

   (L: Imp1; Imp2; ... Impi :L)

(which is not implemented), you should instead write:

   L: (# do Imp1; Imp2; ... Impi #)

In fact, the (L: ... :L) construct is being considered for exclusion from
the BETA language due to the very simple replacement shown above.

See also L22.
----------------------------------------------------------------------------

C06) Why does a BETA program called test.bet cause problems on some UNIX
installations?

By default, the executable generated from a BETA program called test.bet is
called test. Depending on your UNIX installation's defaults and your own
environment variables, attempts to execute the BETA program by typing test
may, however, result in the standard system program test being executed
instead. To avoid the problem, just type ./test instead of test.

Similar problems can arise with other, existing UNIX commands.

[Note: This is a typical beginner's problem, not related to the BETA
language or the BETA environment as such.]
----------------------------------------------------------------------------

C07) How do I disable qualification check warnings?

The "A run-time qualification check will be generated here" warning may be
disabled by using compiler switches. In version v5.0 of the compiler, you
can use the -noquawarn (or -q) switch. All warnings may disabled by using
the -nowarnings (or -w) switch. If you would like the -q option to become
the default, you can include it in your BETAOPTS environment variable, e.g.

   setenv BETAOPTS -q

If you would like to temporarily turn qualification check warnings back on,
you may then do so by specifying the -quawarn switch.

As of version v5.1 of the compiler, the switch -noquawarn have been renamed
to --noWarnQua, and the switch -quawarn have been renamed to --warnQua.
----------------------------------------------------------------------------

C08) What is the difference between P and &P?

Consider the following BETA program:

   (# P: (# do ... #)
   do P; &P
   #)

Compiling this program with the current BETA compiler shows no difference in
the code generated for P and &P.

However, the semantics of BETA defines a difference, namely that P is the
execution of an inserted item and that &P is the creation and execution of a
dynamic item, one of the differences being that inserted items are only
allocated once, irrespectively of how many times they are executed.

The current BETA compiler implements inserted items as dynamic ones, thereby
not taking advantage of the potential possibility for optimization. This
limitation will be removed in a future release of the compiler.
----------------------------------------------------------------------------

C09) What does "virtual prefix not implemented" mean? [corrected in r4.0]

A couple of typos in the compiler manual [MIA 90-02(1.3) August 1994] for
version v5.0 of the compiler have caused some confusion over this message.
Section 5, item 8 ("Implementation Restrictions") should read as follows:

     8. Virtual superpatterns, i.e.,

        A::< (# ... #); (* where A is some virtual *)
        B: A(# ... #);

     have not been implemented.

     By using a final binding, this limitation can often be overcome
     like this:

        A:: (# ... #); (* A is no longer virtual *)
        B: A(# ... #);

     The situation may also occur in a more indirect way:

        graph:
          (# node:< (# ... #);
             nodeList: @list(# element::< node #);
             ...
          #);

     Here the virtual further binding of element in list is not
     allowed, since node is itself virtual.

     The next version of the compiler will allow final binding using a
     pattern that is itself virtual. That is, you will be allowed to do
     this:

        graph:
          (# node:< (# ... #);
             nodeList: @list(# element:: node #);
             ...
          #);

     In version 5.0 of the compiler, this situation is not handled
     correctly. Instead you can do as follows:

        graph:
          (# node:< (# ... #);
             nodeListElement: (# n: ^node enter n[] exit n[] #);
             nodeList: @list(# element::< nodeListElement #);
             ...
          #);

     General virtual prefixes behave much like multiple inheritance and
     will not be implemented in the near future.

These errors have been fixed in the manual for the version v5.1 of the
compiler.
----------------------------------------------------------------------------

C10) What should I do if the compiler prints "Please report the error to
Mjolner Informatics" and stops?

The compiler may under very rare conditions run into an error from which it
is unable to recover. It will often print out the message "Please report the
error to Mjolner Informatics" just before stopping. If you run into an error
like this, you should do the following:

  1. Check in question C11, that the error has not yet been reported.
  2. If it has not been reported, please make an archive with the following
     files (using e.g. tar on UNIX, and e.g. StuffIt or CompactPro on
     macintosh):
        o all relevant .bet source files
        o the .dump file of the compiler, if it exists
        o a file with the compiler output leading to the error
     Then please mail this file to support@mjolner.com with a short
     description of the error.

For users of r4.0, you will find a new tool, betatar, which is usefull for
packing the entire set of source files into a tar-file (only available on
UNIX platforms)
----------------------------------------------------------------------------

C11) What are the known errors in v5.0 of the compiler?

The following paragraphs deals with various bugs and workarounds in the
different compiler versions.
----------------------------------------------------------------------------

C11.1) Bugs in version 5.0 of the compiler

Since the release of v5.0 of the compiler in august 1994, the following
errors have been reported.

Some of these errors occur in very specific situations, that are hard to
describe in general, but others may be generally presented, please see
below.

C11.1.1. Static Constants [fixed in v5.1]

The following program will make the compiler crash:

   ORIGIN '~beta/basiclib/current/betaenv';
   --- program: descriptor ---
   (# E: @(# exit 1 #) #)

The compiler reports:

   ******* System error!!!
   Constant used as static item
   Please report this error to Mjolner Informatics

and then stops.

This is because constants should be declared without the '@' sign, i.e.:

   ORIGIN '~beta/basiclib/current/betaenv';
   --- program: descriptor ---
   (# E: (# exit 1 #) #)

C11.1.2. Computed remotes and virtuals [fixed in v5.1]

The computed remotes, that the compiler supports in general from release
v5.0, will sometimes make the compiler crash, especially if virtuals are
involved. Example:

   ORIGIN '~beta/basiclib/current/betaenv';
   INCLUDE '~beta/containers/current/list';
   --- program: descriptor ---
   (# point: (# x: @integer; #);
      pointList: @List
        (# element::point;
           headx: (# exit (head).elm.x #);
        #);
   #)

This program makes the compiler crash with the error:

   ******* System error!!!
   Pre is empty/null(virtual binding)
   Please report this error to Mjolner Informatics

The workaround in this case is to avoid the computed remote in headx:

   ORIGIN '~beta/basiclib/current/betaenv';
   INCLUDE '~beta/containers/current/list';
   --- program: descriptor ---
   (# point: (# x: @integer; #);
      pointList: @List
        (# element::point;
           thehead: ^theCellType;
           headx: (# do head->thehead[]; exit thehead.elm.x #);
        #);
   #)

C11.1.3. "T1PROGRAM undefined" reported by the linker [fixed in v5.1]

As explained in section 7.3 "Assembler and Linker Errors" in the compiler
reference manual [MIA 90-02], if an unbound SLOT of category Descriptor or
Dopart exist in your program, then this is currently not reported by the
compiler itself, but will be detected as an "Undefined Entry" by the linker.
Especially if you are new to BETA programming, you may wonder why compiling
this fragment (foolib.bet):

   ORIGIN '~beta/basiclib/current/betaenv';
   --- lib: attributes ---
   foo: (# (* ... *) #);

with "beta foolib" causes the linker error "T1PROGRAM undefined". In this
case the reason is that the fragment is actually a library fragment - it
only declares attributes to be used by some program. Specifically the
PROGRAM descriptor SLOT defined in "betaenv" has not been bound, and thus
the error.

The solution is quite simple: Just compile the program as "beta -c foolib"
instead. The next version of the BETA compiler will not attempt to do the
linking if the PROGRAM SLOT is not bound.

If you think this is strange, compare to the equivalent situation in C
(foolib.c)

   foo() { /* ... */ }

If you compile this file with e.g. "cc foolib.c", you will often get the
linker error that "_main" is not defined. The solution here is like in BETA:
"cc -c foolib.c"

Version v5.1 of the compiler may under rare conditions exhibit the above
behaviour, in which case you should use the above workaround, except the the
compiler switch -c in v5.1 have been renamed to -x.

C11.1.4. Reference assignment of repetitions [fixed in v5.1]

Consider the following example:

   ORIGIN '~beta/basiclib/v1.6/betaenv';
   ---  program: descriptor ---
   (# P0: (# #); P1: P0 (# #);
      R1: [5] ^P0;
      R2: [5] ^P1;
   do R1[]->R2[]; (*not legal*)
   #)

It is not legal to assign a repetition reference to another repetition
reference. Unfortunately the compiler does NOT catch this error. The program
compiles and gives unpredictable results when executed.

It is possible to have the following assignment

   R1->R2

which makes R2 be a copy of R1. But R1 and R2 do not refer to the same
repetition.

Note, it is of course possible to have the elemenst of R1 point to the same
elemenst as P1:

   (for i: R1.range repeat R1[i][]->R2[i][] for)

It would be possible to extend BETA to allow assigning a reference to a
repetion object to another reptition, but there are currently no plans for
this.

C11.1.5. Assignment to index variables not checked

The BETA book states that it is not legal to assign to the index variable of
a for-imperative as in:

   (for i: 12 repeat ...; 5->i; ... for)

This restriction is currently not checked by the compiler.

Version v5.1 of the compiler still does not check for these assignments.
----------------------------------------------------------------------------

C11.2) Bugs in version 5.1 of the compiler

Since the release of v5.1 of the compiler ultimo 1995, the following errors
have been reported.

Some of these errors occur in very specific situations, that are hard to
describe in general, but others may be generally presented, please see
below.

C11.2.1) "T1PROGRAM undefined" still reported by the linker

As mentioned in C11.1.3, version 5.1 of the compiler partly fixes the
problem of "T1PROGRAM undefined". To be specific, v5.1 of the compiler
checks, that the PROGRAM slot is met before initiating a call to the linker.

However, it may fail as follows:

   beta frag1 frag2

if frag1 contains a PROGRAM slot, and frag2 does not, you will get the
linker error for frag2: Once a PROGRAM slot has been seen, all fragments
subsequently translated will be attempted linked. This error also happens if
you invoke the compiler as

   beta -r frag1

and then enters frag2 as second fragment to compile when the repeating
compiler asks for it.

Also, if you have declared a Dopart- or Descriptor-slot in one of your
files, and do not have a fragment, that binds these slots in any of the
files in the dependency graph, then the linker may still fail with an
undefined entry for this slot.

See also C11.2.2.

C11.2.2) Other undefined entries (compiler import error) [hpux9pa, nti only]
[corrected in r4.0]

Question:
I experience errors from the linker concerning undefined entries, and I am
sure that all of my slots are bound. What is wrong?

Answer:
You may have encountered a situation where the internal import tables of the
compiler gets confused because two of your slots have identical names.

Consider:

   main.bet:
        ORIGIN '~beta/basiclib/v1.6/betaenv';
        INCLUDE 'foo';
        --PROGRAM: descriptor--
        (#
        do foo
        #)

   foo.bet:
        ORIGIN '~beta/basiclib/v1.6/betaenv';
        BODY 'foobody';
        -- LIB: attributes --
        foo:
          (# size: (# s: @integer <> exit s #);
          do size -> putint; newline;
          #)

   foobody.bet:
        ORIGIN 'foo';
        INCLUDE 'bar';
        -- size: dopart --
        do (&bar[]).size -> s

   bar.bet:
        ORIGIN '~beta/basiclib/v1.6/betaenv';
        BODY 'barbody';
        --LIB: attributes--
        bar:
          (# size: (# s: @integer <> exit s #)#);

   barbody.bet:
        ORIGIN 'bar'
        -- size: dopart --
        do 1 -> s

Although somewhat stupid, you would expect this program to print "1" onto
the screen. And it does so on most platforms. But on the platforms hpux9pa
(HPPA 9000/700 running HP-UX 9) and nti (Windows 95 / Windows NT), when
assembling the code produced for foobody, you get an error like

   undefined label - M2BAR

The reason for this, is that the compiler gets confused by the two dopart
slots both tagged with "size".

The solution is to use two distinct names, e.g. foosize and barsize. Such a
naming scheme is advisable to use in general - notice that if the two SLOTs
had been of kind Descriptor, then on all platforms, you would get

   multiply defined: M1SIZE

C11.2.3) Qualification error in code generation of division expression
[linux, nti only]

Sometimes v5.1 of the compiler on Linux and Windows 95/NT will will crash
with a Qualification Error during code generation of expressions involving
division.

If the resulting dump file starts with something like

   item  in ~beta/.../system/v5.1/LINUXmachine
   -- GDIV-~ in ~beta/.../system/v5.1/LINUXmachine

then it is this error that has occurred.

On linux, the error will occur if you compile e.g. the demo
~beta/demo/r3.1/Xt/awenv/scroll.bet. None of the demos on Windows NT/95
contain expressions that will cause this error, but you may encounter the

Section 4 of 6 - Prev - Next
All sections - 1 - 2 - 3 - 4 - 5 - 6

Back to category Programming - Use Smart Search
Home - Smart Search - About the project - Feedback

© allanswers.org | Terms of use

LiveInternet