Source Code Cross Referenced for ExpressionClassBuilder.java in  » Database-DBMS » db-derby-10.2 » org » apache » derby » impl » sql » compile » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Database DBMS » db derby 10.2 » org.apache.derby.impl.sql.compile 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*
002:
003:           Derby - Class org.apache.derby.impl.sql.compile.ExpressionClassBuilder
004:
005:           Licensed to the Apache Software Foundation (ASF) under one or more
006:           contributor license agreements.  See the NOTICE file distributed with
007:           this work for additional information regarding copyright ownership.
008:           The ASF licenses this file to you under the Apache License, Version 2.0
009:           (the "License"); you may not use this file except in compliance with
010:           the License.  You may obtain a copy of the License at
011:
012:              http://www.apache.org/licenses/LICENSE-2.0
013:
014:           Unless required by applicable law or agreed to in writing, software
015:           distributed under the License is distributed on an "AS IS" BASIS,
016:           WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
017:           See the License for the specific language governing permissions and
018:           limitations under the License.
019:
020:         */
021:
022:        package org.apache.derby.impl.sql.compile;
023:
024:        import org.apache.derby.iapi.services.compiler.ClassBuilder;
025:        import org.apache.derby.iapi.services.compiler.MethodBuilder;
026:        import org.apache.derby.iapi.services.compiler.JavaFactory;
027:        import org.apache.derby.iapi.services.compiler.LocalField;
028:        import org.apache.derby.iapi.reference.ClassName;
029:
030:        import org.apache.derby.iapi.services.sanity.SanityManager;
031:
032:        import org.apache.derby.iapi.sql.compile.CompilerContext;
033:        import org.apache.derby.iapi.sql.compile.ExpressionClassBuilderInterface;
034:
035:        import org.apache.derby.iapi.sql.execute.ResultSetFactory;
036:        import org.apache.derby.iapi.sql.execute.ExecutionFactory;
037:        import org.apache.derby.iapi.sql.execute.ExecIndexRow;
038:
039:        import org.apache.derby.iapi.sql.Activation;
040:        import org.apache.derby.iapi.sql.ParameterValueSet;
041:        import org.apache.derby.iapi.sql.Row;
042:
043:        import org.apache.derby.iapi.sql.execute.ExecRow;
044:
045:        import org.apache.derby.impl.sql.compile.OrderedColumnList;
046:        import org.apache.derby.impl.sql.compile.ResultColumnList;
047:        import org.apache.derby.impl.sql.execute.IndexColumnOrder;
048:        import org.apache.derby.iapi.store.access.ColumnOrdering;
049:
050:        import org.apache.derby.iapi.types.DataValueDescriptor;
051:        import org.apache.derby.iapi.types.DataTypeDescriptor;
052:        import org.apache.derby.iapi.types.DataValueFactory;
053:        import org.apache.derby.iapi.types.TypeId;
054:
055:        import org.apache.derby.iapi.sql.compile.TypeCompiler;
056:
057:        import org.apache.derby.iapi.error.StandardException;
058:        import org.apache.derby.iapi.util.ByteArray;
059:
060:        import org.apache.derby.iapi.services.loader.ClassFactory;
061:        import org.apache.derby.iapi.services.loader.GeneratedClass;
062:        import org.apache.derby.iapi.services.loader.GeneratedByteCode;
063:        import org.apache.derby.iapi.services.loader.GeneratedMethod;
064:
065:        import java.lang.reflect.Modifier;
066:        import org.apache.derby.iapi.services.classfile.VMOpcode;
067:
068:        import org.apache.derby.iapi.services.monitor.Monitor;
069:
070:        import org.apache.derby.iapi.services.io.FormatableArrayHolder;
071:
072:        import java.io.Serializable;
073:
074:        /**
075:         * ExpressionClassBuilder
076:         * provides an interface to satisfy generation's
077:         * common tasks in building classes that involve expressions.
078:         * This is the common superclass of ActivationClassBuilder and
079:         * FilterClassBuilder. See the documentation on ActivationClassBuilder.
080:         *
081:         * @author Rick	Extracted out of ActivationClassBuilder
082:         */
083:        abstract class ExpressionClassBuilder implements 
084:                ExpressionClassBuilderInterface {
085:            ///////////////////////////////////////////////////////////////////////
086:            //
087:            // CONSTANTS
088:            //
089:            ///////////////////////////////////////////////////////////////////////
090:
091:            static final protected String currentDatetimeFieldName = "cdt";
092:
093:            ///////////////////////////////////////////////////////////////////////
094:            //
095:            // STATE
096:            //
097:            ///////////////////////////////////////////////////////////////////////
098:
099:            protected ClassBuilder cb;
100:            protected GeneratedClass gc;
101:            protected int nextExprNum;
102:            protected int nextNonFastExpr;
103:            protected int nextFieldNum;
104:            protected MethodBuilder constructor;
105:            CompilerContext myCompCtx;
106:            MethodBuilder executeMethod; // to find it fast
107:
108:            protected LocalField cdtField;
109:
110:            //protected final JavaFactory javaFac;
111:
112:            private String currentRowScanResultSetName;
113:
114:            ///////////////////////////////////////////////////////////////////////
115:            //
116:            // CONSTRUCTORS
117:            //
118:            ///////////////////////////////////////////////////////////////////////
119:
120:            /**
121:             * By the time this is done, it has constructed the following class:
122:             * <pre>
123:             *    public class #className extends #superClass {
124:             *		public #className() { super(); }
125:             *    }
126:             * </pre>
127:             *
128:             * @exception StandardException thrown on failure
129:             */
130:            ExpressionClassBuilder(String super Class, String className,
131:                    CompilerContext cc) throws StandardException {
132:                int modifiers = Modifier.PUBLIC | Modifier.FINAL;
133:
134:                myCompCtx = cc;
135:                JavaFactory javaFac = myCompCtx.getJavaFactory();
136:
137:                if (className == null) {
138:                    className = myCompCtx.getUniqueClassName();
139:                }
140:
141:                // start the class
142:                cb = javaFac.newClassBuilder(myCompCtx.getClassFactory(),
143:                        getPackageName(), modifiers, className, super Class);
144:
145:                beginConstructor();
146:            }
147:
148:            ///////////////////////////////////////////////////////////////////////
149:            //
150:            // ABSTRACT METHODS TO BE IMPLEMENTED BY CHILDREN
151:            //
152:            ///////////////////////////////////////////////////////////////////////
153:
154:            /**
155:             * Get the name of the package that the generated class will live in.
156:             *
157:             *	@return	name of package that the generated class will live in.
158:             */
159:            abstract String getPackageName();
160:
161:            /**
162:             * Get the number of ExecRows that must be allocated
163:             *
164:             *	@return	number of ExecRows that must be allocated
165:             *
166:             * 	@exception StandardException thrown on failure
167:             */
168:            abstract int getRowCount() throws StandardException;
169:
170:            /**
171:             * Sets the number of subqueries under this expression
172:             *
173:             *
174:             * 	@exception StandardException thrown on failure
175:             */
176:            abstract void setNumSubqueries() throws StandardException;
177:
178:            /**
179:             * Build boiler plate for the Execute method
180:             *
181:             *
182:             *	@return	a method builder containing boiler plate for the Execute method
183:             *
184:             * 	@exception StandardException thrown on failure
185:             */
186:            abstract MethodBuilder beginExecuteMethod()
187:                    throws StandardException;
188:
189:            /**
190:             * Finish up the Execute method.
191:             *
192:             *
193:             * 	@exception StandardException thrown on failure
194:             */
195:            abstract void finishExecuteMethod(boolean genMarkAsTopNode)
196:                    throws StandardException;
197:
198:            ///////////////////////////////////////////////////////////////////////
199:            //
200:            // ACCESSORS
201:            //
202:            ///////////////////////////////////////////////////////////////////////
203:
204:            /**
205:            	Return the base class of the activation's hierarchy
206:            	(the subclass of Object).
207:
208:            	This class is expected to hold methods used by all
209:            	compilation code, such as datatype compilation code,
210:            	e.g. getDataValueFactory.
211:             */
212:            abstract String getBaseClassName();
213:
214:            MethodBuilder getConstructor() {
215:                return constructor;
216:            }
217:
218:            ClassBuilder getClassBuilder() {
219:                return cb;
220:            }
221:
222:            /**
223:             * The execute method returns a result set that will evaluate the
224:             * statement this activation class is the compiled form of.
225:             * REVISIT: do we need to give the caller the ability to touch it
226:             * directly, or could we wrap the alterations to it in this class?
227:             */
228:            MethodBuilder getExecuteMethod() {
229:                return executeMethod;
230:            }
231:
232:            ///////////////////////////////////////////////////////////////////////
233:            //
234:            // CONSTRUCTOR MANAGEMENT
235:            //
236:            ///////////////////////////////////////////////////////////////////////
237:
238:            private final void beginConstructor() {
239:                // create a constructor that just calls super.  
240:                MethodBuilder realConstructor = cb
241:                        .newConstructorBuilder(Modifier.PUBLIC);
242:                realConstructor.callSuper();
243:                realConstructor.methodReturn();
244:                realConstructor.complete();
245:
246:                constructor = cb.newMethodBuilder(Modifier.PUBLIC, "void",
247:                        "postConstructor");
248:                constructor.addThrownException(ClassName.StandardException);
249:            }
250:
251:            /**
252:             * Finish the constructor by newing the array of Rows and putting a return 
253:             * at the end of it.
254:             *
255:             * @exception StandardException thrown on failure
256:             */
257:
258:            void finishConstructor() throws StandardException {
259:                int numResultSets;
260:
261:                /* Set the number of subqueries */
262:                setNumSubqueries();
263:
264:                numResultSets = getRowCount();
265:
266:                /* Generate the new of ExecRow[numResultSets] when there are ResultSets
267:                 * which return Rows.
268:                 */
269:                if (numResultSets >= 1) {
270:                    addNewArrayOfRows(numResultSets);
271:                }
272:
273:                /* Generated code is:
274:                 *		return;
275:                 */
276:                constructor.methodReturn();
277:                constructor.complete();
278:            }
279:
280:            /**
281:             * Generate the assignment for row = new ExecRow[numResultSets]
282:             *
283:             * @param numResultSets	The size of the array.
284:             */
285:            private void addNewArrayOfRows(int numResultSets) {
286:                /* Generated code is:
287:                 *		row = new ExecRow[numResultSets];
288:                 */
289:
290:                constructor.pushThis();
291:                constructor.pushNewArray(ClassName.ExecRow, numResultSets);
292:                constructor.putField(ClassName.BaseActivation, "row",
293:                        ClassName.ExecRow + "[]");
294:                constructor.endStatement();
295:            }
296:
297:            ///////////////////////////////////////////////////////////////////////
298:            //
299:            // ADD FIELDS TO GENERATED CLASS
300:            //
301:            ///////////////////////////////////////////////////////////////////////
302:
303:            /**
304:             * Add a field declaration to the generated class
305:             * 
306:             * @param modifiers	The | of the modifier values such as public, static, etc.
307:             * @param type		The type of the field in java language.
308:             * @param name		The name of the field.
309:             *
310:             * @return None.
311:             */
312:            LocalField newFieldDeclaration(int modifiers, String type,
313:                    String name) {
314:                return cb.addField(type, name, modifiers);
315:            }
316:
317:            /**
318:             * Add an arbitrarily named field to the generated class.
319:             *
320:             * This is used to generate fields where the caller doesn't care what
321:             * the field is named.  It is especially useful for generating arbitrary
322:             * numbers of fields, where the caller doesn't know in advance how many
323:             * fields will be used.  For example, it is used for generating fields
324:             * to hold intermediate values from expressions.
325:             *
326:             * @param modifiers	The | of the modifier values such as public, static, etc.
327:             * @param type		The type of the field in java language.
328:             *
329:             * @return	The name of the new field
330:             */
331:
332:            LocalField newFieldDeclaration(int modifiers, String type) {
333:                return cb.addField(type, newFieldName(), modifiers);
334:            }
335:
336:            ///////////////////////////////////////////////////////////////////////
337:            //
338:            // ADD FUNCTIONS TO GENERATED CLASS
339:            //
340:            ///////////////////////////////////////////////////////////////////////
341:
342:            /**
343:             * Activations might have need of internal functions
344:             * that are not used by the result sets, but by other
345:             * activation functions. Thus, we make it possible
346:             * for functions to be generated directly as well
347:             * as through the newExprFun interface.  newExprFun
348:             * should be used when a static field pointing to the
349:             * expression function is needed.
350:             * <p>
351:             * The generated function will generally have a generated name
352:             * that can be viewed through the MethodBuilder interface.
353:             * This name is generated to ensure uniqueness from other
354:             * function names in the activation class. If you pass in a function
355:             * name, think carefully about whether it will collide with other names.
356:             *
357:             * @param returnType the return type of the function
358:             * @param modifiers the modifiers on the function
359:             *
360:             * @see #newExprFun
361:             */
362:            MethodBuilder newGeneratedFun(String returnType, int modifiers) {
363:
364:                return newGeneratedFun(returnType, modifiers, (String[]) null);
365:            }
366:
367:            MethodBuilder newGeneratedFun(String returnType, int modifiers,
368:                    String[] params) {
369:
370:                String exprName = "g".concat(Integer
371:                        .toString(nextNonFastExpr++));
372:                return newGeneratedFun(exprName, returnType, modifiers, params);
373:
374:            }
375:
376:            private MethodBuilder newGeneratedFun(String exprName,
377:                    String returnType, int modifiers, String[] params) {
378:
379:                //
380:                // create a new method supplying the given modifiers and return Type
381:                // Java: #modifiers #returnType #exprName { }
382:                //
383:                MethodBuilder exprMethod;
384:                if (params == null) {
385:                    exprMethod = cb.newMethodBuilder(modifiers, returnType,
386:                            exprName);
387:                } else {
388:                    exprMethod = cb.newMethodBuilder(modifiers, returnType,
389:                            exprName, params);
390:                }
391:
392:                //
393:                // declare it to throw StandardException
394:                // Java: #modifiers #returnType #exprName throws StandardException { }
395:                //
396:                exprMethod.addThrownException(ClassName.StandardException);
397:
398:                return exprMethod;
399:            }
400:
401:            /**
402:             * "ExprFun"s are the "expression functions" that
403:             * are specific to a given JSQL statement. For example,
404:             * an ExprFun is generated to evaluate the where clause
405:             * of a select statement and return a boolean result.
406:             * <p>
407:             *
408:             * All methods return by this are expected to be called
409:             * via the GeneratedMethod interface. Thus the methods
410:             * are public and return java.lang.Object.
411:             * <p>
412:             * Once the exprfun has been created, the
413:             * caller will need to add statements to it,
414:             * minimally a return statement.
415:             * <p>
416:             * ExprFuns  return Object types, since they
417:             * are invoked through reflection and thus their
418:             * return type would get wrapped in an object anyway.
419:             * For example: return java.lang.Boolean, not boolean.
420:             */
421:            MethodBuilder newExprFun() {
422:                // get next generated function 
423:                String exprName = "e".concat(Integer.toString(nextExprNum++));
424:
425:                return newGeneratedFun(exprName, "java.lang.Object",
426:                        Modifier.PUBLIC, (String[]) null);
427:            }
428:
429:            /**
430:            	Push an expression that is a GeneratedMethod reference to the
431:            	passed in method. aka. a "function pointer".
432:             */
433:            void pushMethodReference(MethodBuilder mb, MethodBuilder exprMethod) {
434:
435:                mb.pushThis(); // instance
436:                mb.push(exprMethod.getName()); // arg
437:                mb.callMethod(VMOpcode.INVOKEINTERFACE,
438:                        ClassName.GeneratedByteCode, "getMethod",
439:                        ClassName.GeneratedMethod, 1);
440:            }
441:
442:            /**
443:             * Start a user expression.  The difference between a normal expression
444:             * (returned by newExprFun)
445:             * and a user expression is that a user expression catches all exceptions
446:             * (because we don't want random exceptions thrown from user methods to
447:             * propagate to the rest of the system.
448:             *
449:             * @return	A new MethodBuilder
450:             */
451:            MethodBuilder newUserExprFun() {
452:
453:                MethodBuilder mb = newExprFun();
454:                mb.addThrownException("java.lang.Exception");
455:                return mb;
456:            }
457:
458:            ///////////////////////////////////////////////////////////////////////
459:            //
460:            // CURRENT DATE/TIME SUPPORT
461:            //
462:            ///////////////////////////////////////////////////////////////////////
463:
464:            /**
465:            	This utility method returns an expression for CURRENT_DATE.
466:            	Get the expression this way, because the activation needs to 
467:            	generate support information for CURRENT_DATE,
468:            	that would otherwise be painful to create manually.
469:             */
470:            void getCurrentDateExpression(MethodBuilder mb) {
471:                // do any needed setup
472:                LocalField lf = getCurrentSetup();
473:
474:                // generated Java:
475:                //	  this.cdt.getCurrentDate();
476:                mb.getField(lf);
477:                mb.callMethod(VMOpcode.INVOKEVIRTUAL, (String) null,
478:                        "getCurrentDate", "java.sql.Date", 0);
479:            }
480:
481:            /**
482:            	This utility method returns an expression for CURRENT_TIME.
483:            	Get the expression this way, because the activation needs to 
484:            	generate support information for CURRENT_TIME,
485:            	that would otherwise be painful to create manually.
486:             */
487:            void getCurrentTimeExpression(MethodBuilder mb) {
488:                // do any needed setup
489:                LocalField lf = getCurrentSetup();
490:
491:                // generated Java:
492:                //	  this.cdt.getCurrentTime();
493:                mb.getField(lf);
494:                mb.callMethod(VMOpcode.INVOKEVIRTUAL, (String) null,
495:                        "getCurrentTime", "java.sql.Time", 0);
496:            }
497:
498:            /**
499:            	This utility method generates an expression for CURRENT_TIMESTAMP.
500:            	Get the expression this way, because the activation needs to 
501:            	generate support information for CURRENT_TIMESTAMP,
502:            	that would otherwise be painful to create manually.
503:             */
504:            void getCurrentTimestampExpression(MethodBuilder mb) {
505:                // do any needed setup
506:                LocalField lf = getCurrentSetup();
507:
508:                // generated Java:
509:                //	  this.cdt.getCurrentTimestamp();
510:                mb.getField(lf);
511:                mb.callMethod(VMOpcode.INVOKEVIRTUAL, (String) null,
512:                        "getCurrentTimestamp", "java.sql.Timestamp", 0);
513:            }
514:
515:            ///////////////////////////////////////////////////////////////////////
516:            //
517:            // COLUMN ORDERING
518:            //
519:            ///////////////////////////////////////////////////////////////////////
520:
521:            /**
522:            	These utility methods buffers compilation from the IndexColumnOrder
523:            	class.
524:
525:            	They create an ordering based on their parameter, stuff that into
526:            	the prepared statement, and then return the entry # for
527:            	use in the generated code.
528:
529:            	We could write another utility method to generate code to
530:            	turn an entry # back into an object, but so far no-one needs it.
531:            
532:            	WARNING: this is a crafty method that ASSUMES that 
533:            	you want every column in the list ordered, and that every
534:            	column in the list is the entire actual result colunm.
535:            	It is only useful for DISTINCT in select.	
536:             */
537:            FormatableArrayHolder getColumnOrdering(ResultColumnList rclist) {
538:                IndexColumnOrder[] ordering;
539:                int numCols = (rclist == null) ? 0 : rclist.size();
540:                //skip the columns which are not exclusively part of the insert list
541:                //ie columns with default and autoincrement. These columns will not
542:                //be part of ordering.
543:                int numRealCols = 0;
544:                for (int i = 0; i < numCols; i++) {
545:                    if (!(rclist.getResultColumn(i + 1)
546:                            .isGeneratedForUnmatchedColumnInInsert()))
547:                        numRealCols++;
548:                }
549:
550:                ordering = new IndexColumnOrder[numRealCols];
551:                for (int i = 0, j = 0; i < numCols; i++) {
552:                    if (!(rclist.getResultColumn(i + 1)
553:                            .isGeneratedForUnmatchedColumnInInsert())) {
554:                        ordering[j] = new IndexColumnOrder(i);
555:                        j++;
556:                    }
557:                }
558:                return new FormatableArrayHolder(ordering);
559:            }
560:
561:            /**
562:             * Add a column to the existing Ordering list.  Takes
563:             * a column id and only adds it if it isn't in the list.
564:             *
565:             *
566:             * @return the ColumnOrdering array
567:             */
568:            FormatableArrayHolder addColumnToOrdering(
569:                    FormatableArrayHolder orderingHolder, int columnNum) {
570:                /*
571:                 ** We don't expect a lot of order by columns, so
572:                 ** linear search.
573:                 */
574:                ColumnOrdering[] ordering = (ColumnOrdering[]) orderingHolder
575:                        .getArray(ColumnOrdering.class);
576:                int length = ordering.length;
577:                for (int i = 0; i < length; i++) {
578:                    if (ordering[i].getColumnId() == columnNum)
579:                        return orderingHolder;
580:                }
581:
582:                /*
583:                 ** Didn't find it.  Allocate a bigger array
584:                 ** and add it to the end
585:                 */
586:                IndexColumnOrder[] newOrdering = new IndexColumnOrder[length + 1];
587:                System.arraycopy(ordering, 0, newOrdering, 0, length);
588:                newOrdering[length] = new IndexColumnOrder(columnNum);
589:
590:                return new FormatableArrayHolder(newOrdering);
591:            }
592:
593:            FormatableArrayHolder getColumnOrdering(OrderedColumnList oclist) {
594:                int numCols = (oclist == null) ? 0 : oclist.size();
595:
596:                if (numCols == 0) {
597:                    return new FormatableArrayHolder(new IndexColumnOrder[0]);
598:                }
599:
600:                return new FormatableArrayHolder(oclist.getColumnOrdering());
601:            }
602:
603:            int addItem(Object o) {
604:                if (SanityManager.DEBUG) {
605:                    if ((o != null) && !(o instanceof  Serializable)) {
606:                        SanityManager
607:                                .THROWASSERT("o ("
608:                                        + o.getClass().getName()
609:                                        + ") expected to be instanceof java.io.Serializable");
610:                    }
611:                }
612:                return myCompCtx.addSavedObject(o);
613:            }
614:
615:            ///////////////////////////////////////////////////////////////////////
616:            //
617:            // Caching resuable Expressions
618:            //
619:            ///////////////////////////////////////////////////////////////////////
620:
621:            /**
622:             * Get/reuse the Expression for getting the DataValueFactory
623:             */
624:            private Object getDVF;
625:
626:            void pushDataValueFactory(MethodBuilder mb) {
627:                // generates:
628:                //	   getDataValueFactory()
629:                //
630:
631:                if (getDVF == null) {
632:                    getDVF = mb.describeMethod(VMOpcode.INVOKEVIRTUAL,
633:                            getBaseClassName(), "getDataValueFactory",
634:                            ClassName.DataValueFactory);
635:                }
636:
637:                mb.pushThis();
638:                mb.callMethod(getDVF);
639:            }
640:
641:            ///////////////////////////////////////////////////////////////////////
642:            //
643:            // RESULT SET SUPPORT
644:            //
645:            ///////////////////////////////////////////////////////////////////////
646:
647:            /**
648:            	This is a utility method to get a common expression --
649:            	"BaseActivation.getResultSetFactory()".
650:            	<p>
651:            	BaseActivation gets the factory from the context and
652:            	caches it for faster retrieval.
653:             */
654:            private Object getRSF;
655:
656:            void pushGetResultSetFactoryExpression(MethodBuilder mb) {
657:                // generated Java:
658:                //	this.getResultSetFactory()
659:                //
660:                if (getRSF == null) {
661:                    getRSF = mb.describeMethod(VMOpcode.INVOKEVIRTUAL,
662:                            getBaseClassName(), "getResultSetFactory",
663:                            ClassName.ResultSetFactory);
664:                }
665:                mb.pushThis();
666:                mb.callMethod(getRSF);
667:            }
668:
669:            /**
670:            	This is a utility method to get a common expression --
671:            	"BaseActivation.getExecutionFactory()".
672:            	REVISIT: could the same expression objects be reused within
673:            	the tree and have the correct java generated each time?
674:            	<p>
675:            	BaseActivation gets the factory from the context and
676:            	caches it for faster retrieval. 
677:             */
678:            private Object getEF;
679:
680:            void pushGetExecutionFactoryExpression(MethodBuilder mb) {
681:                if (getEF == null) {
682:                    getEF = mb.describeMethod(VMOpcode.INVOKEVIRTUAL,
683:                            getBaseClassName(), "getExecutionFactory",
684:                            ClassName.ExecutionFactory);
685:                }
686:
687:                // generated Java:
688:                //	this.getExecutionFactory()
689:                //
690:                mb.pushThis();
691:                mb.callMethod(getEF);
692:            }
693:
694:            /**
695:             * Generate a reference to the row array that
696:             * all activations use.
697:             * 
698:             * @param eb the expression block
699:             *
700:             * @return expression
701:             */
702:            //private void pushRowArrayReference(MethodBuilder mb)
703:            //{ 		
704:            // PUSHCOMPILE - cache
705:            //	mb.pushThis();
706:            //	mb.getField(ClassName.BaseActivation, "row", ClassName.ExecRow + "[]");
707:            //}
708:            /**
709:             * Generate a reference to a colunm in a result set.
710:             * 
711:             * @param rsNumber the result set number
712:             * @param colId the column number
713:             */
714:            void pushColumnReference(MethodBuilder mb, int rsNumber, int colId) {
715:                mb.pushThis();
716:                mb.push(rsNumber);
717:                mb.push(colId);
718:                mb.callMethod(VMOpcode.INVOKEVIRTUAL, ClassName.BaseActivation,
719:                        "getColumnFromRow", ClassName.DataValueDescriptor, 2);
720:
721:                //System.out.println("pushColumnReference ");
722:                //pushRowArrayReference(mb);
723:                //mb.getArrayElement(rsNumber); // instance for getColumn
724:                //mb.push(colId); // first arg
725:                //mb.callMethod(VMOpcode.INVOKEINTERFACE, ClassName.Row, "getColumn", ClassName.DataValueDescriptor, 1);
726:            }
727:
728:            /**
729:             * Generate a reference to the parameter value
730:             * set that all activations use.
731:             * 
732:             */
733:            void pushPVSReference(MethodBuilder mb) {
734:                // PUSHCOMPILER-WASCACHED
735:                mb.pushThis();
736:                mb.getField(ClassName.BaseActivation, "pvs",
737:                        ClassName.ParameterValueSet);
738:            }
739:
740:            ///////////////////////////////////////////////////////////////////////
741:            //
742:            // CLASS IMPLEMENTATION
743:            //
744:            ///////////////////////////////////////////////////////////////////////
745:
746:            /*
747:            	The first time a current datetime is needed, create the class
748:            	level support for it.
749:             */
750:            protected LocalField getCurrentSetup() {
751:                if (cdtField != null)
752:                    return cdtField;
753:
754:                // generated Java:
755:                // 1) the field "cdt" is created:
756:                //    private CurrentDatetime cdt;
757:                cdtField = newFieldDeclaration(Modifier.PRIVATE,
758:                        ClassName.CurrentDatetime, currentDatetimeFieldName);
759:
760:                // 2) the constructor gets a statement to init CurrentDatetime:
761:                //	  cdt = new CurrentDatetime();
762:
763:                constructor.pushNewStart(ClassName.CurrentDatetime);
764:                constructor.pushNewComplete(0);
765:                constructor.setField(cdtField);
766:
767:                return cdtField;
768:            }
769:
770:            /**
771:             * generated the next field name available.
772:             * these are of the form 'e#', where # is
773:             * incremented each time.
774:             * This shares the name space with the expression methods
775:             * as Java allows names and fields to have the same name.
776:             * This reduces the number of constant pool entries created
777:             * for a generated class file.
778:             */
779:            private String newFieldName() {
780:                return "e".concat(Integer.toString(nextFieldNum++));
781:            }
782:
783:            ///////////////////////////////////////////////////////////////////////
784:            //
785:            // DEBUG
786:            //
787:            ///////////////////////////////////////////////////////////////////////
788:
789:            ///////////////////////////////////////////////////////////////////////
790:            //
791:            // DATATYPES
792:            //
793:            ///////////////////////////////////////////////////////////////////////
794:            /**
795:             * Get the TypeCompiler associated with the given TypeId
796:             *
797:             * @param typeId	The TypeId to get a TypeCompiler for
798:             *
799:             * @return	The corresponding TypeCompiler
800:             *
801:             */
802:            protected TypeCompiler getTypeCompiler(TypeId typeId) {
803:                return myCompCtx.getTypeCompilerFactory().getTypeCompiler(
804:                        typeId);
805:            }
806:
807:            ///////////////////////////////////////////////////////////////////////
808:            //
809:            // GENERATE BYTE CODE
810:            //
811:            ///////////////////////////////////////////////////////////////////////
812:
813:            /**
814:             * Take the generated class, and turn it into an
815:             * actual class.
816:             * <p> This method assumes, does not check, that
817:             * the class and its parts are all complete.
818:             *
819:             * @param savedBytes place to save generated bytes.
820:             *	if null, it is ignored
821:             * @exception StandardException thrown when exception occurs
822:             */
823:            GeneratedClass getGeneratedClass(ByteArray savedBytes)
824:                    throws StandardException {
825:                if (gc != null)
826:                    return gc;
827:
828:                if (savedBytes != null) {
829:                    ByteArray classBytecode = cb.getClassBytecode();
830:
831:                    // note: be sure to set the length since
832:                    // the class builder allocates the byte array
833:                    // in big chunks
834:                    savedBytes.setBytes(classBytecode.getArray());
835:                    savedBytes.setLength(classBytecode.getLength());
836:                }
837:
838:                gc = cb.getGeneratedClass();
839:
840:                return gc; // !! yippee !! here it is...
841:            }
842:
843:            /**
844:             * Get a "this" expression declared as an Activation.
845:             * This is the commonly used type of the this expression.
846:             *
847:             */
848:            void pushThisAsActivation(MethodBuilder mb) {
849:                // PUSHCOMPILER - WASCACHED
850:                mb.pushThis();
851:                mb.upCast(ClassName.Activation);
852:            }
853:
854:            /**
855:            	Generate a Null data value.
856:            	Nothing is required on the stack, a SQL null data value
857:            	is pushed.
858:             */
859:            void generateNull(MethodBuilder mb, TypeCompiler tc) {
860:                pushDataValueFactory(mb);
861:                mb.pushNull(tc.interfaceName());
862:                tc.generateNull(mb);
863:            }
864:
865:            /**
866:            	Generate a Null data value.
867:            	The express value is required on the stack and will be popped, a SQL null data value
868:            	is pushed.
869:             */
870:            void generateNullWithExpress(MethodBuilder mb, TypeCompiler tc) {
871:                pushDataValueFactory(mb);
872:                mb.swap(); // need the dvf as the instance
873:                mb.cast(tc.interfaceName());
874:                tc.generateNull(mb);
875:            }
876:
877:            /**
878:            	Generate a data value.
879:            	The value is to be set in the SQL data value is required
880:            	on the stack and will be popped, a SQL data value
881:            	is pushed.
882:             */
883:            void generateDataValue(MethodBuilder mb, TypeCompiler tc,
884:                    LocalField field) {
885:                pushDataValueFactory(mb);
886:                mb.swap(); // need the dvf as the instance
887:                tc.generateDataValue(mb, field);
888:            }
889:
890:            /**
891:             *generates a variable name for the rowscanresultset.
892:             *This can not be a fixed name because in cases like
893:             *cascade delete same activation class will be dealing 
894:             * more than one RowScanResultSets for dependent tables.
895:             */
896:
897:            String newRowLocationScanResultSetName() {
898:                currentRowScanResultSetName = newFieldName();
899:                return currentRowScanResultSetName;
900:            }
901:
902:            // return the Name of ResultSet with the RowLocations to be modified (deleted or updated).
903:            String getRowLocationScanResultSetName() {
904:                return currentRowScanResultSetName;
905:            }
906:
907:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.