File Coverage

blib/lib/COPE/CORBA/ORB.pm
Criterion Covered Total %
statement 13 15 86.6
branch n/a
condition n/a
subroutine 5 5 100.0
pod n/a
total 18 20 90.0


line stmt bran cond sub pod time code
1             # $Id: ORB.pm,v 1.7 1997/07/25 10:12:42 schuller Exp $
2             # Copyright (c) 1997 Lunatech Research / Bart Schuller
3             # See the file "Artistic" in the distribution for licensing and
4             # (lack of) warranties.
5              
6 3     3   5238 use Carp;
  3         7  
  3         223  
7             # interface ORB
8             package CORBA::ORB;
9             $CORBA::ORB::_The_Orb = 0;
10 3     3   17 use strict;
  3         4  
  3         83  
11 3     3   1957 use COPE::CORBA::TypeCode;
  3         8  
  3         18  
12 3     3   15 use COPE::CORBA::TCKind;
  3         14  
  3         12  
13 3     3   1791 use COPE::CORBA::BOA;
  0            
  0            
14             use COPE::CORBA::Exception;
15              
16             my $_byte_order;
17              
18             BEGIN {
19             if (pack('N', 1) eq pack('L', 1)) {
20             $_byte_order = 0;
21             } else {
22             $_byte_order = 1;
23             }
24             }
25              
26             sub new {
27             my($class,$argv,$orb_identifier) = @_;
28             my $self = {
29             byte_order => $_byte_order,
30             };
31              
32             #
33             # Check for -ORBport argument and remove it from
34             # the list of arguments.
35             #
36             if (defined($argv)) {
37             my $x;
38             for ($x=0; $x < $#$argv; $x++) {
39             if ($argv->[$x] eq '-ORBport') {
40             my $orbport = $argv->[$x+1];
41             $orbport =~ s/\D//g;
42             splice(@$argv, $x, 2);
43             if ($orbport){
44             $self->{port} = $orbport;
45             }
46             }
47             }
48             }
49            
50             return $CORBA::ORB::_The_Orb = bless $self, $class;
51             }
52              
53             sub _marshal_boolean {
54             my($out, $index, $byte_order, $data) = @_;
55             $$out.= $data ? "\1" : "\0";
56             $$index++;
57             }
58              
59             sub _marshal_octet {
60             my($out, $index, $byte_order, $data) = @_;
61             $$out .= pack('C', $data);
62             $$index++;
63             }
64              
65             sub _marshal_char {
66             my($out, $index, $byte_order, $data) = @_;
67             $$out .= pack('a', $data);
68             $$index++;
69             }
70              
71             sub _marshal_ushort {
72             my($out, $index, $byte_order, $data) = @_;
73             my $previndex = $$index;
74             $$index = (1+$$index)& ~1;
75             $$out .= "\0" x ($$index-$previndex) . pack($byte_order ? 'v' : 'n', $data);
76             $$index += 2;
77             }
78              
79             sub _marshal_short { _marshal_ushort(@_) }
80              
81             sub _marshal_ulong {
82             my($out, $index, $byte_order, $data) = @_;
83             my $previndex = $$index;
84             $$index = (3+$$index)& ~3;
85             $$out .= "\0" x ($$index-$previndex) . pack($byte_order ? 'V' : 'N', $data);
86             $$index += 4;
87             }
88              
89             sub _marshal_long { _marshal_ulong(@_) }
90              
91             sub _marshal_enum { _marshal_ulong(@_) }
92              
93             sub _marshal_octet_array {
94             my($out, $index, $byte_order, $data, $length) = @_;
95             $$out .= pack("a$length", $data);
96             $$index += $length;
97             }
98              
99             sub _marshal_char_array { _marshal_octet_array(@_) }
100              
101             sub _marshal_string {
102             my($out, $index, $byte_order, $data, $length) = @_;
103             $data .= "\0";
104             _marshal_ulong($out, $index, $byte_order, length($data));
105             $$out .= $data;
106             $$index += length($data);
107             }
108              
109             sub _marshal_octet_sequence {
110             my($out, $index, $byte_order, $data, $length) = @_;
111             _marshal_ulong($out, $index, $byte_order, length($data));
112             $$out .= $data;
113             $$index += length($data);
114             }
115              
116             sub _marshal_sequence {
117             my($out, $index, $byte_order, $data, $_marshal, @extra) = @_;
118             _marshal_ulong($out, $index, $byte_order, scalar(@$data));
119             foreach my $item (@$data) {
120             &$_marshal($out, $index, $byte_order, $item, @extra);
121             }
122             }
123              
124             sub _unmarshal_string {
125             my($in, $index, $byte_order) = @_;
126             $$index = (3+$$index)& ~3;
127             my $length = unpack($byte_order ? 'V' : 'N', substr($$in,$$index,4));
128             $$index += 4;
129             my $string = substr($$in, $$index, $length - 1);
130             $$index += $length;
131             return $string;
132             }
133              
134             sub _unmarshal_octet_sequence {
135             my($in, $index, $byte_order) = @_;
136             $$index = (3+$$index)& ~3;
137             my $length = unpack($byte_order ? 'V' : 'N', substr($$in,$$index,4));
138             $$index += 4;
139             my $string = substr($$in, $$index, $length);
140             $$index += $length;
141             return $string;
142             }
143              
144             sub _unmarshal_char {
145             my($in, $index, $byte_order) = @_;
146             return substr($$in,$$index++,1);
147             }
148              
149             sub _unmarshal_octet {
150             my($in, $index, $byte_order) = @_;
151             return unpack('C', substr($$in,$$index++,1));
152             }
153              
154             sub _unmarshal_boolean { _unmarshal_octet(@_) }
155              
156             sub _unmarshal_octet_array {
157             my($in, $index, $byte_order, $length) = @_;
158             my $oldindex = $$index;
159             $$index += $length;
160             return substr($$in,$oldindex,$length);
161             }
162              
163             sub _unmarshal_char_array { _unmarshal_octet_array(@_) }
164              
165             sub _unmarshal_ushort {
166             my($in, $index, $byte_order) = @_;
167             $$index = (1+$$index)& ~1;
168             my $short = unpack($byte_order ? 'v' : 'n', substr($$in,$$index,2));
169             $$index += 2;
170             return $short;
171             }
172              
173             sub _unmarshal_short {
174             my($in, $index, $byte_order) = @_;
175             $$index = (1+$$index)& ~1;
176             my $tmp = substr($$in,$$index,2);
177             if ($byte_order xor $_byte_order) {
178             $tmp = pack('v', unpack('n', $tmp));
179             }
180             my $short = unpack('s', $tmp);
181             $$index += 2;
182             return $short;
183             }
184              
185             sub _unmarshal_ulong {
186             my($in, $index, $byte_order) = @_;
187             $$index = (3+$$index)& ~3;
188             my $long = unpack($byte_order ? 'V' : 'N', substr($$in,$$index,4));
189             $$index += 4;
190             return $long;
191             }
192              
193             sub _unmarshal_long {
194             my($in, $index, $byte_order) = @_;
195             $$index = (3+$$index)& ~3;
196             my $tmp = substr($$in,$$index,4);
197             if ($byte_order xor $_byte_order) {
198             $tmp = pack('V', unpack('N', $tmp));
199             }
200             my $long = unpack('l', $tmp);
201             $$index += 4;
202             return $long;
203             }
204              
205             sub _unmarshal_enum { _unmarshal_ulong(@_) }
206              
207             sub _unmarshal_sequence {
208             my($in, $index, $byte_order, $_unmarshal, @extra) = @_;
209             $$index = (3+$$index)& ~3;
210             my $num = unpack($byte_order ? 'V' : 'N', substr($$in,$$index,4));
211             $$index += 4;
212             my @self = ();
213             for (my $c = 0; $c < $num; $c++) {
214             push @self, &$_unmarshal($in, $index, $byte_order, @extra);
215             }
216             return \@self;
217             }
218              
219             sub _id2package {
220             my($id) = @_;
221             if ($id =~ m!^IDL:([^/]+/)?(.+):.+$!) {
222             my $package = $2;
223             $package =~ s!/!::!g;
224             return $package;
225             } else {
226             die "_id2package: $id is not a proper RepositoryId";
227             }
228             }
229              
230             BEGIN { $::marshal_depth=0 }
231              
232             sub _marshal_using_tc {
233             my $tc = pop; # sic
234             my $kind = $tc->kind;
235             if ($kind == tk_short) {
236             _marshal_short(@_);
237             return;
238             }
239             if ($kind == tk_boolean) {
240             _marshal_boolean(@_);
241             return;
242             }
243             if ($kind == tk_long) {
244             _marshal_long(@_);
245             return;
246             }
247             if ($kind == tk_ulong) {
248             _marshal_ulong(@_);
249             return;
250             }
251             if ($kind == tk_enum) {
252             _marshal_enum(@_);
253             return;
254             }
255             if ($kind == tk_string) {
256             _marshal_string(@_, $tc->length());
257             return;
258             }
259             if ($kind == tk_sequence) {
260             my $ct = $tc->content_type();
261             if ($ct->kind() == tk_octet) {
262             _marshal_octet_sequence(@_, $tc->length());
263             return;
264             }
265             my $seq = pop;
266             _marshal_ulong(@_, scalar(@$seq));
267             foreach my $item (@$seq) {
268             _marshal_using_tc(@_, $item, $ct);
269             }
270             return;
271             }
272             if ($kind == tk_objref) {
273             my $obj = pop;
274             IOP::IOR::_marshal(@_, $CORBA::ORB::_The_Orb->_object_to_IOR($obj));
275             return;
276             }
277             if ($kind == tk_struct) {
278             my $struct = pop;
279             my $count = $tc->member_count;
280             for (my $counter = 0; $counter < $count; $counter++) {
281             my $element = $struct->{$tc->member_name($counter)};
282             if (!defined($element)) {
283             throw new CORBA::MARSHAL minor => $counter, completion_status => CORBA::CompletionStatus::COMPLETED_MAYBE;
284             }
285             _marshal_using_tc(@_, $element, $tc->member_type($counter));
286             }
287             return;
288             }
289             if ($kind == tk_array) {
290             my $ct = $tc->content_type();
291             if ($ct->kind() == tk_octet) {
292             _marshal_octet_array(@_, $tc->length());
293             return;
294             }
295             my $array = pop;
296             for(my $i=0;$i < $tc->length();$i++) {
297             _marshal_using_tc(@_, $array->[$i], $ct);
298             }
299             return;
300             }
301             if ($kind == tk_except) {
302             my $except = pop;
303             my $count = $tc->member_count;
304             _marshal_string(@_, $tc->id(), 0);
305             for (my $counter = 0; $counter < $count; $counter++) {
306             _marshal_using_tc(@_, $except->{$tc->member_name($counter)}, $tc->member_type($counter));
307             }
308             return;
309             }
310             die "Kind $kind not implemented";
311             }
312              
313             sub _unmarshal_using_tc {
314             my($inref, $indexref, $byte_order, $tc) = @_;
315             my $kind = $tc->kind;
316              
317             if ($kind == tk_void) { return }
318             if ($kind == tk_short) {
319             return _unmarshal_short($inref, $indexref, $byte_order);
320             }
321             if ($kind == tk_long) {
322             return _unmarshal_long($inref, $indexref, $byte_order);
323             }
324             if ($kind == tk_ulong) {
325             return _unmarshal_ulong($inref, $indexref, $byte_order);
326             }
327             if ($kind == tk_boolean) {
328             return _unmarshal_boolean($inref, $indexref, $byte_order);
329             }
330             if ($kind == tk_struct) {
331             my $result = {};
332             my $count = $tc->member_count;
333             for (my $counter = 0; $counter < $count; $counter++) {
334             $result->{$tc->member_name($counter)} = _unmarshal_using_tc(
335             $inref, $indexref, $byte_order, $tc->member_type($counter));
336             }
337             return bless $result, CORBA::ORB::_id2package($tc->id);
338             }
339             if ($kind == tk_sequence) {
340             my $ct = $tc->content_type();
341             if ($ct->kind() == tk_octet) {
342             return _unmarshal_octet_sequence($inref, $indexref, $byte_order);
343             }
344             my $result = [];
345             my $count = _unmarshal_ulong($inref, $indexref, $byte_order);
346             for (my $counter = 0; $counter < $count; $counter++) {
347             $result->[$counter] = _unmarshal_using_tc(
348             $inref, $indexref, $byte_order, $ct);
349             }
350             return $result;
351             }
352             if ($kind == tk_array) {
353             my $ct = $tc->content_type();
354             my $count = $tc->length();
355             if ($ct->kind() == tk_octet) {
356             return _unmarshal_octet_array($inref, $indexref, $byte_order, $count);
357             }
358             my $result = [];
359             for (my $counter = 0; $counter < $count; $counter++) {
360             $result->[$counter] = _unmarshal_using_tc(
361             $inref, $indexref, $byte_order, $ct);
362             }
363             return $result;
364             }
365             if ($kind == tk_string) {
366             return _unmarshal_string($inref, $indexref, $byte_order);
367             }
368             if ($kind == tk_TypeCode) {
369             return CORBA::TypeCode::_unmarshal($inref, $indexref, $byte_order);
370             }
371             if ($kind == tk_enum) {
372             return _unmarshal_enum($inref, $indexref, $byte_order);
373             }
374             if ($kind == tk_objref) {
375             my $ior = IOP::IOR::_unmarshal($inref, $indexref, $byte_order);
376             my $object = CORBA::Object->_new_from_ior($ior);
377             return bless $object, CORBA::ORB::_id2package($tc->id);
378             }
379             if ($kind == tk_except) {
380             my $result = {};
381             my $count = $tc->member_count;
382             for (my $counter = 0; $counter < $count; $counter++) {
383             $result->{$tc->member_name($counter)} = _unmarshal_using_tc(
384             $inref, $indexref, $byte_order, $tc->member_type($counter));
385             }
386             return bless $result, CORBA::ORB::_id2package($tc->id);
387             }
388             if ($kind == tk_any) {
389             my $result = {_type => CORBA::TypeCode::_unmarshal($inref, $indexref, $byte_order) };
390             $result->{_value} = _unmarshal_using_tc($inref, $indexref, $byte_order, $result->{_type});
391             return $result;
392             }
393             die "Kind $kind not implemented";
394             }
395              
396             sub BOA_init (;$$) {
397             return new CORBA::BOA @_;
398             }
399              
400             use COPE::IOP;
401             use COPE::CORBA::Object;
402              
403             sub _object_to_IOR {
404             my($self,$impl) = @_;
405             my $ior;
406             if ($impl) {
407             if ("$impl" =~ /=HASH/ && $impl->{_ior}) {
408             return $impl->{_ior}; # impl is really a client-side stub Object
409             # TODO use UNIVERSAL?
410             }
411             my $boa = $CORBA::BOA::_The_Boa;
412             my $obj = $boa->{skeletons}{$impl};
413             if ($obj->{_ior}) {
414             return $obj->{_ior};
415             }
416             my $profilebody = new IIOP::ProfileBody (
417             iiop_version => new IIOP::Version (major=>chr(1),minor=>chr(0)),
418             host => $boa->{host},
419             port => $boa->{port},
420             object_key => $obj->{id} );
421             my $profile_data = chr($boa->{byte_order});
422             my $index = 1;
423             IIOP::ProfileBody::_marshal(\$profile_data, \$index, $boa->{byte_order}, $profilebody);
424             my $taggedprofile = new IOP::TaggedProfile (
425             tag => IOP::TAG_INTERNET_IOP,
426             profile_data => $profile_data );
427             $ior = new IOP::IOR (
428             type_id => $obj->{interface},
429             profiles => [ $taggedprofile ] );
430             $obj->{_ior} = $ior;
431             } else {
432             $ior = new IOP::IOR (
433             type_id => '',
434             profiles => [] );
435             }
436             return $ior;
437             }
438              
439             sub object_to_string {
440             my($self,$impl) = @_;
441             my $boa = $CORBA::BOA::_The_Boa;
442             my $m_ior = chr($boa->{byte_order});
443             my $ior = $self->_object_to_IOR($impl);
444             my $index = 1;
445             IOP::IOR::_marshal(\$m_ior, \$index, $boa->{byte_order}, $ior);
446             my $hex = 'IOR:';
447             for (my $i = 0; $i < length($m_ior); $i++) {
448             $hex .= sprintf("%02X", unpack('C', substr($m_ior, $i, 1)));
449             }
450             return $hex;
451             }
452              
453             sub string_to_object {
454             my($self,$str) = @_;
455             my $hex = substr($str,4);
456             my $m_ior = '';
457             for (my $i = 0; $i < length($hex); $i += 2) {
458             $m_ior .= pack('C', hex(join('',unpack('aa', substr($hex, $i, 2)))));
459             }
460             my $byte_order = unpack('C', substr($m_ior, 0, 1));
461             # skip first byte
462             my $index = 1;
463             my $ior = IOP::IOR::_unmarshal(\$m_ior, \$index, $byte_order);
464             return CORBA::Object->_new_from_ior($ior, $self);
465             }
466              
467             sub list_initial_services {
468             return [ qw/
469             NameService
470             InterfaceRepository
471             /];
472             }
473              
474             require COPE::Announcer;
475              
476             sub resolve_initial_references {
477             my($self, $objectid) = @_;
478             return $self->string_to_object(COPE::Announcer::resolve($objectid));
479             }
480              
481             package CORBA::_Struct;
482              
483             sub new ($%) {
484             my($class, %self) = @_;
485             bless \%self, $class;
486             }
487              
488             package CORBA;
489              
490             sub ORB_init (;$$) {
491             return new CORBA::ORB @_;
492             }
493              
494             1;