Copyright (C) 2000-2012 |
Manpages INTERNALSSection: User Contributed Perl Documentation (1)Updated: 2000-09-03 Index Return to Main Contents NAMEPDL::Internals - description of the current internalsDESCRIPTIONIntroThis document explains various aspects of the current implementation of PDL. If you just want to use PDL for something, you definitely do not need to read this. Even if you want to interface your C routines to PDL or create new PDL::PP functions, you do not need to read this (though it may be informative). This document is primarily intended for people interested in debugging or changing the internals of PDL. To read this, a good understanding of the C language and programming and data structures in general is required, as well as some perl understanding. If you read through this document and understand all of it and are able to point what any part of this document refers to in the PDL core sources and additionally struggle to understand PDL::PP, you will be awarded the title ``PDL Guru'' (of course, the current version of this document is so incomplete that this is not yet the case).Warning: If it seems that this document has gotten out of date, please inform the PerlDL developers email list (address in the README file) about it. This may well happen. PiddlesCurrently, a pdl data object is a hash ref which contains the element PDL, which is a pointer to a pdl structure, as well as some other fields. The file "Core.pm" uses some of these fields and the file "pdlhash.c" converts these to C when necessary.The pdl struct is defined in "pdl.h" and the meanings of the fields are
TransformationsEach transformation has a virtual table which contains various information about that transformation. Usually transformations are generated with PDL::PP so it's better to see that documentation.FreeingCurrently, not much is freed, especially when dataflow is done. This is bound to change pretty soon.ThreadingThe file "pdlthread.c" handles most of the threading matters. The threading is encapsulated in the structure "pdlthread.h".Accessing children and parents of a piddleThe file Basic/Core/pdlapi.h.PL contains useful routines for manipulating the pdl structure (it's probably easier to read Basic/Core/pdlapi.h once you've performed a build of PDL).An example of processing the children of a piddle is provided by the "baddata" method of PDL::Bad (only available if you have comiled PDL with the "WITH_BADVAL" option set to 1, but still useful as an example!). Consider the following situation:
perldl> $a = rvals(7,7,Centre=>[3,4]); perldl> $b = $a->slice('2:4,3:5'); perldl> ? vars PDL variables in package main:: Name Type Dimension Flow State Mem ---------------------------------------------------------------- $a Double D [7,7] P 0.38Kb $b Double D [3,3] VC 0.00KbNow, if I suddenly decide that $a should be flagged as possibly containing bad values, using
perldl> $a->baddata(1)then I want the state of $b - it's child - to be changed as well, so that I get a 'B' in the State field:
perldl> ? vars PDL variables in package main:: Name Type Dimension Flow State Mem ---------------------------------------------------------------- $a Double D [7,7] PB 0.38Kb $b Double D [3,3] VCB 0.00KbThis bit of magic is performed by the "propogate_badflag" function, which is listed below:
/* newval = 1 means set flag, 0 means clear it */ /* thanks to Christian Soeller for this */ void propogate_badflag( pdl *it, int newval ) { PDL_DECL_CHILDLOOP(it) PDL_START_CHILDLOOP(it) { pdl_trans *trans = PDL_CHILDLOOP_THISCHILD(it); int i; for( i = trans->vtable->nparents; i < trans->vtable->npdls; i++ ) { pdl *child = trans->pdls[i]; if ( newval ) child->state |= PDL_BADVAL; else child->state &= ~PDL_BADVAL; /* make sure we propogate to grandchildren, etc */ propogate_badflag( child, newval ); } /* for: i */ } PDL_END_CHILDLOOP(it) } /* propogate_badflag */Given a piddle ("pdl *it"), the routine loops through each "pdl_trans" structure, where access to this structure is provided by the "PDL_CHILDLOOP_THISCHILD" macro. The children of the piddle are stored in the "pdls" array, after the parents, hence the loop from "i = ...nparents" to "i = ...nparents - 1". Once we have the pointer to the child piddle, we can do what we want to it; here we change the value of the "state" variable, but the details are unimportant). What is important is that we call "propogate_badflag" on this piddle, to ensure we loop through its children. This recursion ensures we get to all the offspring of a particular piddle. THE FOLLOWING NEEDS TO BE CHECKED. Access to parents is similar, with the "for" loop replaced by:
for( i = 0; i < trans->vtable->nparents; i++ ) { AUTHORCopyright(C) 1997 Tuomas J. Lukka (lukka@fas.harvard.edu), 2000 Doug Burke (burke@ifa.hawaii.edu).Redistribution in the same form is allowed but reprinting requires a permission from the author.
Index
This document was created by man2html, using the manual pages. Time: 18:26:02 GMT, November 06, 2024 |