|
FAUST compiler
0.9.9.6b8
|
00001 /************************************************************************ 00002 ************************************************************************ 00003 FAUST compiler 00004 Copyright (C) 2003-2004 GRAME, Centre National de Creation Musicale 00005 --------------------------------------------------------------------- 00006 This program is free software; you can redistribute it and/or modify 00007 it under the terms of the GNU General Public License as published by 00008 the Free Software Foundation; either version 2 of the License, or 00009 (at your option) any later version. 00010 00011 This program is distributed in the hope that it will be useful, 00012 but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00014 GNU General Public License for more details. 00015 00016 You should have received a copy of the GNU General Public License 00017 along with this program; if not, write to the Free Software 00018 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 00019 ************************************************************************ 00020 ************************************************************************/ 00021 00022 00023 00024 #include "sigtype.hh" 00025 #include "compatibility.hh" 00026 #include <stdio.h> 00027 00028 #include "sigprint.hh" 00029 #include "sigtyperules.hh" 00030 #include "privatise.hh" 00031 00032 00033 /***************************************************************************** 00034 privatise : compile a list of signals 00035 *****************************************************************************/ 00036 00037 static Tree makePrivatisationKey(const Tree& t); 00038 static Tree makePrivatisationLabel(const Tree& exp); 00039 00040 static Tree privatisation (const Tree& k, const Tree& t); 00041 static Tree computePrivatisation (const Tree& k, const Tree& t); 00042 static Tree labelize(const Tree& label, const Tree& exp); 00043 00044 00045 Tree privatise(const Tree& t) 00046 { 00047 00048 return privatisation(makePrivatisationKey(t), t); 00049 } 00050 00051 00052 // -- implementation ----------------- 00053 00054 static Tree makePrivatisationKey(const Tree& t) 00055 { 00056 char name[256]; 00057 snprintf(name, 256, "PRIVATISE %p : ", (CTree*)t); 00058 return tree(unique(name)); 00059 } 00060 00061 static Tree makePrivatisationLabel(const Tree& t) 00062 { 00063 char name[256]; 00064 snprintf(name, 256, "OWNER IS %p : ", (CTree*)t); 00065 return tree(unique(name)); 00066 } 00067 00068 00069 // -- implementation ----------------- 00070 00071 static Tree privatisation (const Tree& k, const Tree& t) 00072 { 00073 Tree v; 00074 00075 if (t->arity() == 0) { 00076 return t; 00077 00078 } else if (getProperty(t, k, v)) { 00079 /* Terme deja visité. La propriété nous indique 00080 la version privatisée ou nil si elle est identique 00081 au terme initial. 00082 */ 00083 return isNil(v) ? t : v; 00084 00085 } else { 00086 /* Calcul du terme privatisé et mis à jour 00087 de la propriété. Nil indique que le terme 00088 privatisé est identique à celui de depart 00089 (pour eviter les boucles avec les compteurs 00090 de references) 00091 */ 00092 v = computePrivatisation(k,t); 00093 if (v != t) { 00094 setProperty(t, k, v ); 00095 } else { 00096 setProperty(t, k, nil); 00097 } 00098 return v; 00099 } 00100 } 00101 00102 static Tree computePrivatisation(const Tree& k, const Tree& exp) 00103 { 00104 Tree tbl, size, idx, wrt, content, id, var, body; 00105 00106 if ( isSigWRTbl(exp, id, tbl, idx, wrt) ) { 00107 /* Ce qui ne peut pas être partagé, ce sont les 00108 tables dans lesquelles on ecrit. Pour cela 00109 on leur donne un label unique 00110 */ 00111 return sigWRTbl( 00112 id, 00113 labelize( makePrivatisationLabel(exp), privatisation(k, tbl) ), 00114 privatisation(k, idx), 00115 privatisation(k, wrt) ); 00116 00117 } else if ( isSigTable(exp, id, size, content) ) { 00118 /* Rien à privatiser dans une table (car size est 00119 censée etre une expression entiere) 00120 */ 00121 return exp; 00122 00123 } else if ( isSigGen(exp, content) ) { 00124 /* On ne visite pas les contenus des tables 00125 */ 00126 printf("erreur 1 dans computePrivatisation\n"); 00127 exit(1); 00128 00129 } else if ( isRec(exp, var, body) ) { 00130 /* On ne visite pas les contenus des tables 00131 */ 00132 setProperty(exp, k, nil); 00133 return rec(var, privatisation(k,body)); 00134 00135 } else { 00136 /* On parcours les autres arbres en privatisant les branches 00137 */ 00138 int n = exp->arity(); 00139 00140 switch (n) { 00141 00142 case 1 : 00143 return tree( 00144 exp->node(), 00145 privatisation(k, exp->branch(0)) ); 00146 case 2 : 00147 return tree( 00148 exp->node(), 00149 privatisation(k, exp->branch(0)), 00150 privatisation(k, exp->branch(1)) ); 00151 case 3 : 00152 return tree ( 00153 exp->node(), 00154 privatisation(k, exp->branch(0)), 00155 privatisation(k, exp->branch(1)), 00156 privatisation(k, exp->branch(2)) ); 00157 case 4 : 00158 return tree ( 00159 exp->node(), 00160 privatisation(k, exp->branch(0)), 00161 privatisation(k, exp->branch(1)), 00162 privatisation(k, exp->branch(2)), 00163 privatisation(k, exp->branch(3)) ); 00164 } 00165 printf("erreur 2 dans computePrivatisation\n"); 00166 exit(1); 00167 } 00168 printf("situation anormale dans computePrivatisation\n"); 00169 return exp; 00170 } 00171 00172 static Tree labelize(const Tree& newid, const Tree& exp) 00173 { 00174 Tree tbl, size, idx, wrt, content, oldid; 00175 00176 if ( isSigWRTbl(exp, oldid, tbl, idx, wrt) ) { 00177 /* Ce qui ne peut pas être partagé, ce sont les 00178 tables dans lesquelles on ecrit. Pour cela 00179 on leur donne un label unique 00180 */ 00181 return sigWRTbl(newid, tbl, idx, wrt); 00182 00183 } else if ( isSigTable(exp, oldid, size, content) ) { 00184 /* Rien à privatiser dans une table (car size est 00185 censée etre une expression entiere) 00186 */ 00187 return sigTable(newid, size, content); 00188 00189 } else { 00190 00191 printf("erreur labelize\n"); 00192 exit(1); 00193 } 00194 00195 return exp; 00196 } 00197
1.8.0