From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on polar.synack.me X-Spam-Level: X-Spam-Status: No, score=-0.8 required=5.0 tests=BAYES_00,INVALID_DATE autolearn=no autolearn_force=no version=3.4.4 X-Google-Language: ENGLISH,ASCII-7-bit X-Google-Thread: 103376,7f9c4ba3b0dc13ca X-Google-Attributes: gid103376,public X-Google-ArrivalTime: 1994-12-17 19:29:27 PST Path: nntp.gmd.de!newsserver.jvnc.net!news.cac.psu.edu!news.pop.psu.edu!hudson.lm.com!godot.cc.duq.edu!newsfeed.pitt.edu!gatech!darwin.sura.net!source.asset.com!source.asset.com!not-for-mail From: bishopm@source.asset.com (Michael M. Bishop) Newsgroups: comp.lang.ada Subject: Re: Addressing functions (long) Date: 17 Dec 1994 02:23:58 -0500 Organization: Asset Source for Software Engineering Technology Message-ID: <3cu3me$fvd@source.asset.com> References: <3citrc$bb5@earth.usa.net> <3clisk$9th@felix.seas.gwu.edu> NNTP-Posting-Host: 530tr0 Date: 1994-12-17T02:23:58-05:00 List-Id: In article <3clisk$9th@felix.seas.gwu.edu>, Michael Feldman wrote: >In article <3citrc$bb5@earth.usa.net>, Bill Buckley wrote: >> >>High Ada lovers, I've got a question on storing subprogram address in >>Ada. I know I can get the address of a subprogram via the ADDRESS >>attribute in Ada but can not figure a way to use it. I don't have any >>immediate need for such a procedure but it has my old C-C++ courisity >>wondering. For instance if I were to have an array of subprogram addresses >>A(1..2) => (1 => Print1'ADDRESS, >> 2 => Print2'ADDRESS); >>how could I implement the calling these functions (note : I know the >>syntax above is wrong but can't get this simple editor to back up to >>change it). I have heard from several other Ada programmers that this >>may not be possible. > >You can usually get something reasonably meaningful by casting the address >to an integer. Instantiate Unchecked_Conversion: > >FUNCTION AddressToInt IS NEW Unchecked_Conversion > (Source => System.Address, Target => Integer); > >you can then use a normal Integer_IO instance to display it. If the >instance is called My_Int_IO, then > > My_Int_IO.Put(Item => AddressToInt(Print1'Address), Base => 16); > >should display it nicely in hexadecimal. > >Mike Feldman I think Bill is asking about a way to call the above functions whose addresses are stored in the array. I've done this by passing the subprogram addresses to a C function that does the actual calling. This might be a compiler-specific solution as it uses pragmas. I'm using SunAda version 1.1 on SunOS 4.1. The C routine looks like this (in this example, I'm passing a parameter back to the Ada procedure): pragma Wierd_C_Stuff (On); void call_procedure_with_a_parameter (proc_addr, parm) int proc_addr; double parm; /* use whatever parameter type you need */ { union { int procedure_address; void (*procedure) (); } proc_union; proc_union.procedure_address = proc_addr; proc_union.procedure (parm); } pragma Wierd_C_Stuff (Off); I may have messed up the syntax for the procedure pointer member of the union. I apologize if I did. In order to interface the above C function with Ada, I need a couple of pragmas. pragma Interface (C, call_procedure_with_a_parameter); procedure Procedure_To_Be_Called (Parm : in Float) is -- in SunAda, Float is equivalent to C's double begin < whatever goes here > end Procedure_To_Be_Called; pragma External (C, Procedure_To_Be_Called); procedure Call_Procedure_By_Address is begin Call_Procedure_With_A_Parameter (Procedure_To_Be_Called'address, 3.1416); end Call_Procedure_By_Address; The pragma External informs the compiler that Procedure_To_Be_Called will be called by a C function. I hope this helps. -- | Mike Bishop | The opinions expressed here reflect | | bishopm@source.asset.com | those of this station, its management, | | Member: Team Ada | and the entire world. |