[comp.sys.amiga.programmer] Need help accessing MathTrans library from Task

jason@longhorn.austin.ibm.com (Jason Lowdermilk) (03/08/91)

I'm having a problem accessing the transcendental math library from a 
"child task" created with CreateTask, in particular the sqrt function.
I'm using Lattice 5 under WB 1.3. I think I understand why a Task can  
not use functions in the DOS library, but I can not think of any reason
why a Task would not be able to access the transcendental library, since
this does not involve "owning" any resources. Functions from other
libraries, including the FFP library, work fine. Does anyone have
experience with this?                                                    

-- 
Jason Lowdermilk
  internet: jason@longhorn.austin.ibm.com
  UUCP: @cs.utexas.edu:ibmchs!auschs!longhorn.austin.ibm.com!jason
  VNET: LOWDERMI@DALVM41B

jap@convex.cl.msu.edu (Joe Porkka) (03/12/91)

jason@longhorn.austin.ibm.com (Jason Lowdermilk) writes:

>I'm having a problem accessing the transcendental math library from a 
>"child task" created with CreateTask, in particular the sqrt function.
>I'm using Lattice 5 under WB 1.3. I think I understand why a Task can  
>not use functions in the DOS library, but I can not think of any reason
This is because DOS expects there to be some extra info appened to the
end of the Task structure, which is only present when you are a process.

The only gotcha would be that OpenLibrary() requires you to
be a process, so unless your main process does the
OpenLibrary for the child task, you have the potential to
go BOOM.

Its not clear from you posting, but is SQRT the only function
your using from that lib, or the only function from that lib giving
you greif?

markv@kuhub.cc.ukans.edu (03/12/91)

In article <5778@awdprime.UUCP>, jason@longhorn.austin.ibm.com (Jason Lowdermilk) writes:
> I'm having a problem accessing the transcendental math library from a 
> "child task" created with CreateTask, in particular the sqrt function.
> I'm using Lattice 5 under WB 1.3. I think I understand why a Task can  
> not use functions in the DOS library, but I can not think of any reason
> why a Task would not be able to access the transcendental library, since
> this does not involve "owning" any resources. Functions from other
> libraries, including the FFP library, work fine. Does anyone have
> experience with this?                                                    

A task can call MathTrans library.  It cannot always call
OpenLibrary("mathtrans.library",34L); because if the library is not in
memory, then Exec will call LoadSeg() to get the library in memory,
which is guarenteed to be a one way trip to la-la land if it isn't a process.

So, the parent of the child needs to OpenLibrary() so that the library
is in memory.  Then the child can get the base from the parent
(easy to do if child is a function in the parent and they share global
data), otherwise the child can call OpenLibrary() as long as the
parent holds mathtrans.library open to keep it in memory.

Note that this applies to *all* disk based libraries (although some
libs that are disk based in 1.3 are in ROM for 2.0).
 
> -- 
> Jason Lowdermilk
>   internet: jason@longhorn.austin.ibm.com
>   UUCP: @cs.utexas.edu:ibmchs!auschs!longhorn.austin.ibm.com!jason
>   VNET: LOWDERMI@DALVM41B
-- 
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Mark Gooderum			Only...		\    Good Cheer !!!
Academic Computing Services	       ///	  \___________________________
University of Kansas		     ///  /|         __    _
Bix:	  mgooderum	      \\\  ///  /__| |\/| | | _   /_\  makes it
Bitnet:   MARKV@UKANVAX		\/\/  /    | |  | | |__| /   \ possible...
Internet: markv@kuhub.cc.ukans.edu
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

dale@boing.UUCP (Dale Luck) (03/12/91)

In article <1991Mar11.202919.21272@msuinfo.cl.msu.edu> jap@convex.cl.msu.edu (Joe Porkka) writes:
>jason@longhorn.austin.ibm.com (Jason Lowdermilk) writes:
>
>>I'm having a problem accessing the transcendental math library from a 
>>"child task" created with CreateTask, in particular the sqrt function.
>
>The only gotcha would be that OpenLibrary() requires you to
>be a process, so unless your main process does the
>OpenLibrary for the child task, you have the potential to
>go BOOM.
>

I think you could get around this by calling OpenLibrary of mathtrans in
the process that starts the task before starting the task that needs
the sqrt function. The first thing the new task should do though is
another OpenLibrary of mathtrans also for it's own use. The first OpenLibrary
will guarentee the library is loaded and running and therefore the other
task(nonprocess) will not need to worry about OpenLibrary running off
to do some DOS stuff.

I don't know if this action is guarenteed or spelled out, but it seems
logical to me. Would be nice if OpenLibrary would actually use another
process to do that work though instead of the current tasks context, thereby
making OpenLibrary a safe task only function.

A point to be made: Each task must call OpenLibrary when using the
math libraries. It is illegal to for a new task to use the  context of
another task when using the math libraries.

The reason:
Floating point chips need to maintain per task context. They are
initialized for the current task only when OpenLibrary is called.

-- 
Dale Luck     GfxBase/Boing, Inc.
{uunet!cbmvax|pyramid}!amiga!boing!dale

jason@longhorn.austin.ibm.com (Jason Lowdermilk) (03/13/91)

In article <29024.27db9dce@kuhub.cc.ukans.edu> markv@kuhub.cc.ukans.edu writes:
>> I'm having a problem accessing the transcendental math library from a 
>> "child task" created with CreateTask, in particular the sqrt function.
>
>A task can call MathTrans library.  It cannot always call
>OpenLibrary("mathtrans.library",34L); because if the library is not in
>memory, then Exec will call LoadSeg() to get the library in memory,
>which is guarenteed to be a one way trip to la-la land if it isn't a process.
>
>So, the parent of the child needs to OpenLibrary() so that the library
>is in memory.  Then the child can get the base from the parent
>(easy to do if child is a function in the parent and they share global
>data), otherwise the child can call OpenLibrary() as long as the
>parent holds mathtrans.library open to keep it in memory.
>

The parent process opens the mathtrans library prior to creating the child.
The parent also calls sqrt() several times before creating the child. Sqrt 
is the the only transcendental function I am using, although I can
duplicate the problem by calling some other function such as sin().
I have worked around this problem by writing my own sqrt routine as a 
function (in fact it is several times faster than the system sqrt,
albeit less accurate), but I am still curious why this doesn't work. I can 
put together a minimal code example that illustrates this and post it tomorrow. 

-- 
Jason Lowdermilk
  internet: jason@longhorn.austin.ibm.com
  UUCP: @cs.utexas.edu:ibmchs!auschs!longhorn.austin.ibm.com!jason
  VNET: LOWDERMI@DALVM41B

markv@kuhub.cc.ukans.edu (03/13/91)

In article <5847@awdprime.UUCP>, jason@longhorn.austin.ibm.com (Jason Lowdermilk) writes:
> In article <29024.27db9dce@kuhub.cc.ukans.edu> markv@kuhub.cc.ukans.edu writes:
>>> I'm having a problem accessing the transcendental math library from a 
>>> "child task" created with CreateTask, in particular the sqrt function.
>>
>>A task can call MathTrans library.  It cannot always call
>>OpenLibrary("mathtrans.library",34L); because if the library is not in
>>memory, then Exec will call LoadSeg() to get the library in memory,
>>which is guarenteed to be a one way trip to la-la land if it isn't a process.
>>
>>So, the parent of the child needs to OpenLibrary() so that the library
>>is in memory.  Then the child can get the base from the parent
>>(easy to do if child is a function in the parent and they share global
>>data), otherwise the child can call OpenLibrary() as long as the
>>parent holds mathtrans.library open to keep it in memory.
>>
> 
> The parent process opens the mathtrans library prior to creating the child.
> The parent also calls sqrt() several times before creating the child. Sqrt 
> is the the only transcendental function I am using, although I can
> duplicate the problem by calling some other function such as sin().

Hmm.  Let's try a simpler answer.  Are you using a function as the
child task?  If so, and you want the child to use the parents library
base, the child needs to be able access global data.  If the program
is 32 bit abs addressing (-b0) then nothing needs to be done.  If the
program is base-relative (-b1) then the child task function needs to
establish the base register, either by declaring the function
__saveds, compiling with -Y, or calling geta4() early in the function.

If, you have a debugger, run the parent until MathTransBase is valid
and note its value.  Then set a breakpoint in the child on a call to
the math function and go.  When you trap the break point step through
the code until you get to the actual JSR instruction for the function.
With inline functions (which I assume your using), A5 should (*must*)
contain the value of MathTransBase.  If not, the library base somehow
isn't valid.  If so then you have other problems.

> I have worked around this problem by writing my own sqrt routine as a 
> function (in fact it is several times faster than the system sqrt,
> albeit less accurate).

As a side note, 2.0 has a single precision IEEE lib that will use the
FPU if available and gives performance close the the FFP routines of
1.3 even w/o the FPU.

>but I am still curious why this doesn't work. I can 
>put together a minimal code example that illustrates this and post it tomorrow

Yeah, this might work better than trying to guess what your doing...

> 
> -- 
> Jason Lowdermilk
>   internet: jason@longhorn.austin.ibm.com
>   UUCP: @cs.utexas.edu:ibmchs!auschs!longhorn.austin.ibm.com!jason
>   VNET: LOWDERMI@DALVM41B
-- 
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Mark Gooderum			Only...		\    Good Cheer !!!
Academic Computing Services	       ///	  \___________________________
University of Kansas		     ///  /|         __    _
Bix:	  mgooderum	      \\\  ///  /__| |\/| | | _   /_\  makes it
Bitnet:   MARKV@UKANVAX		\/\/  /    | |  | | |__| /   \ possible...
Internet: markv@kuhub.cc.ukans.edu
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

bhgs@gpu.utcs.utoronto.ca (R. Holdom) (03/14/91)

In article <29036.27dcecfb@kuhub.cc.ukans.edu> markv@kuhub.cc.ukans.edu writes:
>In article <5847@awdprime.UUCP>, jason@longhorn.austin.ibm.com (Jason Lowdermilk) writes:
>> In article <29024.27db9dce@kuhub.cc.ukans.edu> markv@kuhub.cc.ukans.edu writes:
>>>> I'm having a problem accessing the transcendental math library from a 
>>>> "child task" created with CreateTask, in particular the sqrt function.
>>>
>>>A task can call MathTrans library.  It cannot always call
>>>OpenLibrary("mathtrans.library",34L); because if the library is not in
>>>memory, then Exec will call LoadSeg() to get the library in memory,
>>>which is guarenteed to be a one way trip to la-la land if it isn't a process.
>>>
>>>So, the parent of the child needs to OpenLibrary() so that the library
>>>is in memory.  Then the child can get the base from the parent
>>>(easy to do if child is a function in the parent and they share global
>>>data), otherwise the child can call OpenLibrary() as long as the
>>>parent holds mathtrans.library open to keep it in memory.
>>>
>> 
>> The parent process opens the mathtrans library prior to creating the child.
>> The parent also calls sqrt() several times before creating the child. Sqrt 
>> is the the only transcendental function I am using, although I can
>> duplicate the problem by calling some other function such as sin().
>
>Hmm.  Let's try a simpler answer.  Are you using a function as the
>child task?  If so, and you want the child to use the parents library
>base, the child needs to be able access global data.  If the program
>is 32 bit abs addressing (-b0) then nothing needs to be done.  If the
>program is base-relative (-b1) then the child task function needs to
>establish the base register, either by declaring the function
>__saveds, compiling with -Y, or calling geta4() early in the function.
>
>If, you have a debugger, run the parent until MathTransBase is valid
>and note its value.  Then set a breakpoint in the child on a call to
>the math function and go.  When you trap the break point step through
>the code until you get to the actual JSR instruction for the function.
>With inline functions (which I assume your using), A5 should (*must*)
>contain the value of MathTransBase.  If not, the library base somehow
>isn't valid.  If so then you have other problems.
>
>> I have worked around this problem by writing my own sqrt routine as a 
>> function (in fact it is several times faster than the system sqrt,
>> albeit less accurate).
>
>As a side note, 2.0 has a single precision IEEE lib that will use the
>FPU if available and gives performance close the the FFP routines of
>1.3 even w/o the FPU.
>
>>but I am still curious why this doesn't work. I can 
>>put together a minimal code example that illustrates this and post it tomorrow
>
>Yeah, this might work better than trying to guess what your doing...
>

  I recall reading in the libraries/devices book that the library
pointer to the math libraries should NOT be shared between processes.
This may well be the root of your problems.  The reason is that if
you have an FPU installed, the state of the FPU is saved in the
data area, offset from the library pointer, during a task switch.
Some useful information may be saved there even if you don't have
an FPU installed.  This, of coarse, is only the answer if you take
the library pointer directly from your parent process.  If you do,
then instead you should open the library from your parent process,
to make sure it is in ram, and then open it again in your task, which
should be OK 'cause now its in memory.
                   Just my 2 bits worth.
                              Jon Spencer.

dale@boing.UUCP (Dale Luck) (03/14/91)

In article <29036.27dcecfb@kuhub.cc.ukans.edu> markv@kuhub.cc.ukans.edu writes:
>In article <5847@awdprime.UUCP>, (Jason Lowdermilk) writes:
>So, the parent of the child needs to OpenLibrary() so that the library
>is in memory.  Then the child can get the base from the parent
>(easy to do if child is a function in the parent and they share global
>data), otherwise the child can call OpenLibrary() as long as the
>parent holds mathtrans.library open to keep it in memory.

This is not supported and can lead to unexpected results, especially if
both parent and child then try to use the same library. All tasks must
open the math libraries for themselves. Sharing LibBase pointers is illegal.

To get around the 'feature' in OpenLibrary needing a Process in case the
library is disk based you should open it first by the parent and then
open it a second time by the child. You should also not store the variable
in the same place since the return from the OpenLibrary call could be
different even though you are opening the same library.

>As a side note, 2.0 has a single precision IEEE lib that will use the
>FPU if available and gives performance close the the FFP routines of
>1.3 even w/o the FPU.

Sharing LibBase ptrs here is guarenteed to be illegal and a mistake.

-- 
Dale Luck     GfxBase/Boing, Inc.
{uunet!cbmvax|pyramid}!amiga!boing!dale