source: branches/0.20.x/abcl/src/org/armedbear/lisp/Package.java

Last change on this file was 12431, checked in by Mark Evenson, 15 years ago

Replace FastStringBuffer? with java.lang.StringBuilder?.

Phil Hudson suggested in Feburary 2009 that "[FastStringBuffer?] should
be removed with all references to it replaced with
java.lang.StringBuilder? once enough confidence in this change has been
gained." After almost a year of using FastStringBuffer? as a delagate
for StringBuilder?, that confidence has indeed been gained.

One subtlety for use of StringBuilder?: there is no

StringBuilder?(char)

constructor, so use

StringBuilder?(String.valueOf(c))

to construct a new StringBuilder? containing a single char. Otherwise
that char will get promoted to an int, and you will invoke

StringBuilder?(int capacity)

which will "swallow" the first character that you thought you were adding.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
File size: 28.7 KB
Line 
1/*
2 * Package.java
3 *
4 * Copyright (C) 2002-2007 Peter Graves <peter@armedbear.org>
5 * $Id: Package.java 12431 2010-02-08 08:05:15Z mevenson $
6 *
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation; either version 2
10 * of the License, or (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
20 *
21 * As a special exception, the copyright holders of this library give you
22 * permission to link this library with independent modules to produce an
23 * executable, regardless of the license terms of these independent
24 * modules, and to copy and distribute the resulting executable under
25 * terms of your choice, provided that you also meet, for each linked
26 * independent module, the terms and conditions of the license of that
27 * module.  An independent module is a module which is not derived from
28 * or based on this library.  If you modify this library, you may extend
29 * this exception to your version of the library, but you are not
30 * obligated to do so.  If you do not wish to do so, delete this
31 * exception statement from your version.
32 */
33
34package org.armedbear.lisp;
35
36import static org.armedbear.lisp.Lisp.*;
37
38import java.util.ArrayList;
39import java.util.HashMap;
40import java.util.Iterator;
41import java.util.List;
42
43public final class Package extends LispObject
44{
45    private String name;
46    private SimpleString lispName;
47
48    private LispObject propertyList;
49
50    private final SymbolHashTable internalSymbols = new SymbolHashTable(16);
51    private final SymbolHashTable externalSymbols = new SymbolHashTable(16);
52
53    private HashMap<String,Symbol> shadowingSymbols;
54    private ArrayList<String> nicknames;
55    private LispObject useList = null;
56    private ArrayList<Package> usedByList = null;
57
58    // Anonymous package.
59    public Package()
60    {
61    }
62
63    public Package(String name)
64    {
65        this.name = name;
66        lispName = new SimpleString(name);
67    }
68
69    public Package(String name, int size)
70    {
71        this.name = name;
72        lispName = new SimpleString(name);
73    }
74
75    @Override
76    public LispObject typeOf()
77    {
78        return Symbol.PACKAGE;
79    }
80
81    @Override
82    public LispObject classOf()
83    {
84        return BuiltInClass.PACKAGE;
85    }
86
87    @Override
88    public LispObject getDescription()
89    {
90        if (name != null) {
91            StringBuilder sb = new StringBuilder("The ");
92            sb.append(name);
93            sb.append(" package");
94            return new SimpleString(sb);
95        }
96        return new SimpleString("PACKAGE");
97    }
98
99    @Override
100    public LispObject typep(LispObject type)
101    {
102        if (type == Symbol.PACKAGE)
103            return T;
104        if (type == BuiltInClass.PACKAGE)
105            return T;
106        return super.typep(type);
107    }
108
109    public final String getName()
110    {
111        return name;
112    }
113
114    public final LispObject NAME()
115    {
116        return lispName != null ? lispName : NIL;
117    }
118
119    @Override
120    public final LispObject getPropertyList()
121    {
122        if (propertyList == null)
123            propertyList = NIL;
124        return propertyList;
125    }
126
127    @Override
128    public final void setPropertyList(LispObject obj)
129    {
130        if (obj == null)
131            throw new NullPointerException();
132        propertyList = obj;
133    }
134
135    public final List getNicknames()
136    {
137        return nicknames;
138    }
139
140    public final synchronized boolean delete()
141    {
142        if (name != null) {
143            Packages.deletePackage(this);
144            List internals = internalSymbols.getSymbols();
145            for (int i = internals.size(); i-- > 0;) {
146                Symbol symbol = (Symbol) internals.get(i);
147                if (symbol.getPackage() == this)
148                    symbol.setPackage(NIL);
149                internalSymbols.remove(symbol);
150            }
151            List externals = externalSymbols.getSymbols();
152            for (int i = externals.size(); i-- > 0;) {
153                Symbol symbol = (Symbol) externals.get(i);
154                if (symbol.getPackage() == this)
155                    symbol.setPackage(NIL);
156                externalSymbols.remove(symbol);
157            }
158            name = null;
159            lispName = null;
160            nicknames = null;
161            return true;
162        }
163        return false;
164    }
165
166    public final synchronized void rename(String newName, LispObject newNicks)
167
168    {
169        ArrayList<String> arrayList = null;
170        while (newNicks != NIL) {
171            if (arrayList == null)
172                arrayList = new ArrayList<String>();
173            arrayList.add(javaString(newNicks.car()));
174            newNicks = newNicks.cdr();
175        }
176        // Remove old name and nicknames from Packages map.
177        Packages.deletePackage(this);
178        // Now change the names...
179        name = newName;
180        lispName = new SimpleString(newName);
181        nicknames = arrayList;
182        // And add the package back.
183        Packages.addPackage(this);
184    }
185
186    public synchronized Symbol findInternalSymbol(SimpleString name)
187    {
188        return internalSymbols.get(name);
189    }
190
191    public synchronized Symbol findExternalSymbol(SimpleString name)
192    {
193        return externalSymbols.get(name);
194    }
195
196    public synchronized Symbol findExternalSymbol(SimpleString name, int hash)
197    {
198        return externalSymbols.get(name, hash);
199    }
200
201    // Returns null if symbol is not accessible in this package.
202    public synchronized Symbol findAccessibleSymbol(String name)
203
204    {
205        return findAccessibleSymbol(new SimpleString(name));
206    }
207
208    // Returns null if symbol is not accessible in this package.
209    public synchronized Symbol findAccessibleSymbol(SimpleString name)
210
211    {
212        // Look in external and internal symbols of this package.
213        Symbol symbol = externalSymbols.get(name);
214        if (symbol != null)
215            return symbol;
216        symbol = internalSymbols.get(name);
217        if (symbol != null)
218            return symbol;
219        // Look in external symbols of used packages.
220        if (useList instanceof Cons) {
221            LispObject usedPackages = useList;
222            while (usedPackages != NIL) {
223                Package pkg = (Package) usedPackages.car();
224                symbol = pkg.findExternalSymbol(name);
225                if (symbol != null)
226                    return symbol;
227                usedPackages = usedPackages.cdr();
228            }
229        }
230        // Not found.
231        return null;
232    }
233
234    public synchronized LispObject findSymbol(String name)
235
236    {
237        final SimpleString s = new SimpleString(name);
238        final LispThread thread = LispThread.currentThread();
239        // Look in external and internal symbols of this package.
240        Symbol symbol = externalSymbols.get(s);
241        if (symbol != null)
242            return thread.setValues(symbol, Keyword.EXTERNAL);
243        symbol = internalSymbols.get(s);
244        if (symbol != null)
245            return thread.setValues(symbol, Keyword.INTERNAL);
246        // Look in external symbols of used packages.
247        if (useList instanceof Cons) {
248            LispObject usedPackages = useList;
249            while (usedPackages != NIL) {
250                Package pkg = (Package) usedPackages.car();
251                symbol = pkg.findExternalSymbol(s);
252                if (symbol != null)
253                    return thread.setValues(symbol, Keyword.INHERITED);
254                usedPackages = usedPackages.cdr();
255            }
256        }
257        // Not found.
258        return thread.setValues(NIL, NIL);
259    }
260
261    // Helper function to add NIL to PACKAGE_CL.
262    public synchronized void addSymbol(Symbol symbol)
263    {
264        Debug.assertTrue(symbol.getPackage() == this);
265        Debug.assertTrue(symbol.getName().equals("NIL"));
266        externalSymbols.put(symbol.name, symbol);
267    }
268
269    private synchronized Symbol addSymbol(SimpleString name, int hash)
270    {
271        Symbol symbol = new Symbol(name, hash, this);
272        if (this == PACKAGE_KEYWORD) {
273            symbol.initializeConstant(symbol);
274            externalSymbols.put(name, symbol);
275        } else
276            internalSymbols.put(name, symbol);
277       
278        return symbol;
279    }
280
281    public synchronized Symbol addInternalSymbol(String symbolName)
282    {
283        final Symbol symbol = new Symbol(symbolName, this);
284        internalSymbols.put(symbol);
285        return symbol;
286    }
287
288    public synchronized Symbol addExternalSymbol(String symbolName)
289    {
290        final Symbol symbol = new Symbol(symbolName, this);
291        externalSymbols.put(symbol);
292        return symbol;
293    }
294
295    public synchronized Symbol intern(String symbolName)
296    {
297        return intern(new SimpleString(symbolName));
298    }
299
300    public synchronized Symbol intern(SimpleString symbolName)
301    {
302        final int hash = symbolName.sxhash();
303        // Look in external and internal symbols of this package.
304        Symbol symbol = externalSymbols.get(symbolName, hash);
305        if (symbol != null)
306            return symbol;
307        symbol = internalSymbols.get(symbolName, hash);
308        if (symbol != null)
309            return symbol;
310        // Look in external symbols of used packages.
311        if (useList instanceof Cons) {
312            LispObject usedPackages = useList;
313            while (usedPackages != NIL) {
314                Package pkg = (Package) usedPackages.car();
315                symbol = pkg.findExternalSymbol(symbolName, hash);
316                if (symbol != null)
317                    return symbol;
318                usedPackages = usedPackages.cdr();
319            }
320        }
321        // Not found.
322        return addSymbol(symbolName, hash);
323    }
324
325    public synchronized Symbol intern(final SimpleString s,
326                                      final LispThread thread)
327    {
328        final int hash = s.sxhash();
329        // Look in external and internal symbols of this package.
330        Symbol symbol = externalSymbols.get(s, hash);
331        if (symbol != null)
332            return (Symbol) thread.setValues(symbol, Keyword.EXTERNAL);
333        symbol = internalSymbols.get(s, hash);
334        if (symbol != null)
335            return (Symbol) thread.setValues(symbol, Keyword.INTERNAL);
336        // Look in external symbols of used packages.
337        if (useList instanceof Cons) {
338            LispObject usedPackages = useList;
339            while (usedPackages != NIL) {
340                Package pkg = (Package) usedPackages.car();
341                symbol = pkg.findExternalSymbol(s, hash);
342                if (symbol != null)
343                    return (Symbol) thread.setValues(symbol, Keyword.INHERITED);
344                usedPackages = usedPackages.cdr();
345            }
346        }
347        // Not found.
348        return (Symbol) thread.setValues(addSymbol(s, hash), NIL);
349    }
350
351    public synchronized Symbol internAndExport(String symbolName)
352
353    {
354        final SimpleString s = new SimpleString(symbolName);
355        final int hash = s.sxhash();
356        // Look in external and internal symbols of this package.
357        Symbol symbol = externalSymbols.get(s, hash);
358        if (symbol != null)
359            return symbol;
360        symbol = internalSymbols.get(s, hash);
361        if (symbol != null) {
362            export(symbol);
363            return symbol;
364        }
365        if (useList instanceof Cons) {
366            // Look in external symbols of used packages.
367            LispObject usedPackages = useList;
368            while (usedPackages != NIL) {
369                Package pkg = (Package) usedPackages.car();
370                symbol = pkg.findExternalSymbol(s, hash);
371                if (symbol != null) {
372                    export(symbol);
373                    return symbol;
374                }
375                usedPackages = usedPackages.cdr();
376            }
377        }
378        // Not found.
379        symbol = new Symbol(s, hash, this);
380        if (this == PACKAGE_KEYWORD)
381            symbol.initializeConstant(symbol);
382        externalSymbols.put(s, symbol);
383        return symbol;
384    }
385
386    public synchronized LispObject unintern(final Symbol symbol)
387
388    {
389        final String symbolName = symbol.getName();
390        final boolean shadow;
391        if (shadowingSymbols != null && shadowingSymbols.get(symbolName) == symbol)
392            shadow = true;
393        else
394            shadow = false;
395        if (shadow) {
396            // Check for conflicts that might be exposed in used package list
397            // if we remove the shadowing symbol.
398            Symbol sym = null;
399            if (useList instanceof Cons) {
400                LispObject usedPackages = useList;
401                while (usedPackages != NIL) {
402                    Package pkg = (Package) usedPackages.car();
403                    Symbol s = pkg.findExternalSymbol(symbol.name);
404                    if (s != null) {
405                        if (sym == null)
406                            sym = s;
407                        else if (sym != s) {
408                            StringBuilder sb =
409                                new StringBuilder("Uninterning the symbol ");
410                            sb.append(symbol.getQualifiedName());
411                            sb.append(" causes a name conflict between ");
412                            sb.append(sym.getQualifiedName());
413                            sb.append(" and ");
414                            sb.append(s.getQualifiedName());
415                            return error(new PackageError(sb.toString()));
416                        }
417                    }
418                    usedPackages = usedPackages.cdr();
419                }
420            }
421        }
422        // Reaching here, it's OK to remove the symbol.
423        if (internalSymbols.get(symbol.name) == symbol)
424            internalSymbols.remove(symbol.name);
425        else if (externalSymbols.get(symbol.name) == symbol)
426            externalSymbols.remove(symbol.name);
427        else
428            // Not found.
429            return NIL;
430        if (shadow) {
431            Debug.assertTrue(shadowingSymbols != null);
432            shadowingSymbols.remove(symbolName);
433        }
434        if (symbol.getPackage() == this)
435            symbol.setPackage(NIL);
436        return T;
437    }
438
439    public synchronized void importSymbol(Symbol symbol)
440    {
441        if (symbol.getPackage() == this)
442            return; // Nothing to do.
443        Symbol sym = findAccessibleSymbol(symbol.name);
444        if (sym != null && sym != symbol) {
445            StringBuilder sb = new StringBuilder("The symbol ");
446            sb.append(sym.getQualifiedName());
447            sb.append(" is already accessible in package ");
448            sb.append(name);
449            sb.append('.');
450            error(new PackageError(sb.toString()));
451        }
452        internalSymbols.put(symbol.name, symbol);
453        if (symbol.getPackage() == NIL)
454            symbol.setPackage(this);
455    }
456
457    public synchronized void export(final Symbol symbol)
458    {
459        final String symbolName = symbol.getName();
460        boolean added = false;
461        if (symbol.getPackage() != this) {
462            Symbol sym = findAccessibleSymbol(symbol.name);
463            if (sym != symbol) {
464                StringBuilder sb = new StringBuilder("The symbol ");
465                sb.append(symbol.getQualifiedName());
466                sb.append(" is not accessible in package ");
467                sb.append(name);
468                sb.append('.');
469                error(new PackageError(sb.toString()));
470                return;
471            }
472            internalSymbols.put(symbol.name, symbol);
473            added = true;
474        }
475        if (added || internalSymbols.get(symbol.name) == symbol) {
476            if (usedByList != null) {
477                for (Iterator it = usedByList.iterator(); it.hasNext();) {
478                    Package pkg = (Package) it.next();
479                    Symbol sym = pkg.findAccessibleSymbol(symbol.name);
480                    if (sym != null && sym != symbol) {
481                        if (pkg.shadowingSymbols != null &&
482                            pkg.shadowingSymbols.get(symbolName) == sym) {
483                            // OK.
484                        } else {
485                            StringBuilder sb = new StringBuilder("The symbol ");
486                            sb.append(sym.getQualifiedName());
487                            sb.append(" is already accessible in package ");
488                            sb.append(pkg.getName());
489                            sb.append('.');
490                            error(new PackageError(sb.toString()));
491                            return;
492                        }
493                    }
494                }
495            }
496            // No conflicts.
497            internalSymbols.remove(symbol.name);
498            externalSymbols.put(symbol.name, symbol);
499            return;
500        }
501        if (externalSymbols.get(symbol.name) == symbol)
502            // Symbol is already exported; there's nothing to do.
503            return;
504        StringBuilder sb = new StringBuilder("The symbol ");
505        sb.append(symbol.getQualifiedName());
506        sb.append(" is not accessible in package ");
507        sb.append(name);
508        sb.append('.');
509        error(new PackageError(sb.toString()));
510    }
511
512    public synchronized void unexport(final Symbol symbol)
513
514    {
515        if (symbol.getPackage() == this) {
516            if (externalSymbols.get(symbol.name) == symbol) {
517                externalSymbols.remove(symbol.name);
518                internalSymbols.put(symbol.name, symbol);
519            }
520        } else {
521            // Signal an error if symbol is not accessible.
522            if (useList instanceof Cons) {
523                LispObject usedPackages = useList;
524                while (usedPackages != NIL) {
525                    Package pkg = (Package) usedPackages.car();
526                    if (pkg.findExternalSymbol(symbol.name) == symbol)
527                        return; // OK.
528                    usedPackages = usedPackages.cdr();
529                }
530            }
531            StringBuilder sb = new StringBuilder("The symbol ");
532            sb.append(symbol.getQualifiedName());
533            sb.append(" is not accessible in package ");
534            sb.append(name);
535            error(new PackageError(sb.toString()));
536        }
537    }
538
539    public synchronized void shadow(final String symbolName)
540
541    {
542        if (shadowingSymbols == null)
543            shadowingSymbols = new HashMap<String,Symbol>();
544        final SimpleString s = new SimpleString(symbolName);
545        Symbol symbol = externalSymbols.get(s);
546        if (symbol != null) {
547            shadowingSymbols.put(symbolName, symbol);
548            return;
549        }
550        symbol = internalSymbols.get(s);
551        if (symbol != null) {
552            shadowingSymbols.put(symbolName, symbol);
553            return;
554        }
555        if (shadowingSymbols.get(symbolName) != null)
556            return;
557        symbol = new Symbol(s, this);
558        internalSymbols.put(s, symbol);
559        shadowingSymbols.put(symbolName, symbol);
560    }
561
562    public synchronized void shadowingImport(Symbol symbol)
563    {
564        LispObject where = NIL;
565        final String symbolName = symbol.getName();
566        Symbol sym = externalSymbols.get(symbol.name);
567        if (sym != null) {
568            where = Keyword.EXTERNAL;
569        } else {
570            sym = internalSymbols.get(symbol.name);
571            if (sym != null) {
572                where = Keyword.INTERNAL;
573            } else {
574                // Look in external symbols of used packages.
575                if (useList instanceof Cons) {
576                    LispObject usedPackages = useList;
577                    while (usedPackages != NIL) {
578                        Package pkg = (Package) usedPackages.car();
579                        sym = pkg.findExternalSymbol(symbol.name);
580                        if (sym != null) {
581                            where = Keyword.INHERITED;
582                            break;
583                        }
584                        usedPackages = usedPackages.cdr();
585                    }
586                }
587            }
588        }
589        if (sym != null) {
590            if (where == Keyword.INTERNAL || where == Keyword.EXTERNAL) {
591                if (sym != symbol) {
592                    if (shadowingSymbols != null)
593                        shadowingSymbols.remove(symbolName);
594                    unintern(sym);
595                }
596            }
597        }
598        internalSymbols.put(symbol.name, symbol);
599        if (shadowingSymbols == null)
600            shadowingSymbols = new HashMap<String,Symbol>();
601        Debug.assertTrue(shadowingSymbols.get(symbolName) == null);
602        shadowingSymbols.put(symbolName, symbol);
603    }
604
605    // "USE-PACKAGE causes PACKAGE to inherit all the external symbols of
606    // PACKAGES-TO-USE. The inherited symbols become accessible as internal
607    // symbols of PACKAGE."
608    public void usePackage(Package pkg)
609    {
610        if (useList == null)
611            useList = NIL;
612        if (!memq(pkg, useList)) {
613            // "USE-PACKAGE checks for name conflicts between the newly
614            // imported symbols and those already accessible in package."
615            List symbols = pkg.getExternalSymbols();
616            for (int i = symbols.size(); i-- > 0;) {
617                Symbol symbol = (Symbol) symbols.get(i);
618                Symbol existing = findAccessibleSymbol(symbol.name);
619                if (existing != null && existing != symbol) {
620                    if (shadowingSymbols == null ||
621                        shadowingSymbols.get(symbol.getName()) == null)
622                    {
623                        error(new PackageError("A symbol named " + symbol.getName() +
624                                                " is already accessible in package " +
625                                                name + "."));
626                        return;
627                    }
628                }
629            }
630            useList = useList.push(pkg);
631            // Add this package to the used-by list of pkg.
632            if (pkg.usedByList != null)
633                Debug.assertTrue(!pkg.usedByList.contains(this));
634            if (pkg.usedByList == null)
635                pkg.usedByList = new ArrayList<Package>();
636            pkg.usedByList.add(this);
637        }
638    }
639
640    public void unusePackage(Package pkg)
641    {
642        if (useList instanceof Cons) {
643            if (memq(pkg, useList)) {
644                // FIXME Modify the original list instead of copying it!
645                LispObject newList = NIL;
646                while (useList != NIL) {
647                    if (useList.car() != pkg)
648                        newList = newList.push(useList.car());
649                    useList = useList.cdr();
650                }
651                useList = newList.nreverse();
652                Debug.assertTrue(!memq(pkg, useList));
653                Debug.assertTrue(pkg.usedByList != null);
654                Debug.assertTrue(pkg.usedByList.contains(this));
655                pkg.usedByList.remove(this);
656            }
657        }
658    }
659
660    public final void addNickname(String s)
661    {
662        // This call will signal an error if there's a naming conflict.
663        Packages.addNickname(this, s);
664
665        if (nicknames != null) {
666            if (nicknames.contains(s))
667                return; // Nothing to do.
668        } else
669            nicknames = new ArrayList<String>();
670
671        nicknames.add(s);
672    }
673
674    public String getNickname()
675    {
676        if (nicknames != null && nicknames.size() > 0)
677            return (String) nicknames.get(0);
678        return null;
679    }
680
681    public LispObject packageNicknames()
682    {
683        LispObject list = NIL;
684        if (nicknames != null) {
685            for (int i = nicknames.size(); i-- > 0;) {
686                String nickname = (String) nicknames.get(i);
687                list = new Cons(new SimpleString(nickname), list);
688            }
689        }
690        return list;
691    }
692
693    public LispObject getUseList()
694    {
695        if (useList == null)
696            useList = NIL;
697        return useList;
698    }
699
700    public boolean uses(LispObject pkg)
701    {
702        return (useList instanceof Cons) && memq(pkg, useList);
703    }
704
705    public LispObject getUsedByList()
706    {
707        LispObject list = NIL;
708        if (usedByList != null) {
709            for (Iterator it = usedByList.iterator(); it.hasNext();) {
710                Package pkg = (Package) it.next();
711                list = new Cons(pkg, list);
712            }
713        }
714        return list;
715    }
716
717    public LispObject getShadowingSymbols()
718    {
719        LispObject list = NIL;
720        if (shadowingSymbols != null) {
721            for (Iterator it = shadowingSymbols.values().iterator(); it.hasNext();) {
722                Symbol symbol = (Symbol) it.next();
723                list = new Cons(symbol, list);
724            }
725        }
726        return list;
727    }
728
729    public synchronized List getExternalSymbols()
730    {
731        return externalSymbols.getSymbols();
732    }
733
734    public synchronized List<Symbol> getAccessibleSymbols()
735    {
736        ArrayList<Symbol> list = new ArrayList<Symbol>();
737        list.addAll(internalSymbols.getSymbols());
738        list.addAll(externalSymbols.getSymbols());
739        if (useList instanceof Cons) {
740            LispObject usedPackages = useList;
741            while (usedPackages != NIL) {
742                Package pkg = (Package) usedPackages.car();
743                List<Symbol> symbols = pkg.externalSymbols.getSymbols();
744                for (int i = 0; i < symbols.size(); i++) {
745                    Symbol symbol = (Symbol) symbols.get(i);
746                    if (shadowingSymbols == null || shadowingSymbols.get(symbol.getName()) == null)
747                        list.add(symbol);
748                }
749                usedPackages = usedPackages.cdr();
750            }
751        }
752        return list;
753    }
754
755    public synchronized LispObject PACKAGE_INTERNAL_SYMBOLS()
756    {
757        LispObject list = NIL;
758        List symbols = internalSymbols.getSymbols();
759        for (int i = symbols.size(); i-- > 0;)
760            list = new Cons((Symbol)symbols.get(i), list);
761        return list;
762    }
763
764    public synchronized LispObject PACKAGE_EXTERNAL_SYMBOLS()
765    {
766        LispObject list = NIL;
767        List symbols = externalSymbols.getSymbols();
768        for (int i = symbols.size(); i-- > 0;)
769            list = new Cons((Symbol)symbols.get(i), list);
770        return list;
771    }
772
773    public synchronized LispObject PACKAGE_INHERITED_SYMBOLS()
774    {
775        LispObject list = NIL;
776        if (useList instanceof Cons) {
777            LispObject usedPackages = useList;
778            while (usedPackages != NIL) {
779                Package pkg = (Package) usedPackages.car();
780                List externals = pkg.getExternalSymbols();
781                for (int i = externals.size(); i-- > 0;) {
782                    Symbol symbol = (Symbol) externals.get(i);
783                    if (shadowingSymbols != null && shadowingSymbols.get(symbol.getName()) != null)
784                        continue;
785                    if (externalSymbols.get(symbol.name) == symbol)
786                        continue;
787                    list = new Cons(symbol, list);
788                }
789                usedPackages = usedPackages.cdr();
790            }
791        }
792        return list;
793    }
794
795    public synchronized LispObject getSymbols()
796    {
797        LispObject list = NIL;
798        List internals = internalSymbols.getSymbols();
799        for (int i = internals.size(); i-- > 0;)
800            list = new Cons((Symbol)internals.get(i), list);
801        List externals = externalSymbols.getSymbols();
802        for (int i = externals.size(); i-- > 0;)
803            list = new Cons((Symbol)externals.get(i), list);
804        return list;
805    }
806
807    public synchronized Symbol[] symbols()
808    {
809        List internals = internalSymbols.getSymbols();
810        List externals = externalSymbols.getSymbols();
811        Symbol[] array = new Symbol[internals.size() + externals.size()];
812        int i = 0;
813        for (Iterator it = internals.iterator(); it.hasNext();) {
814            Symbol symbol = (Symbol) it.next();
815            array[i++] = symbol;
816        }
817        for (Iterator it = externals.iterator(); it.hasNext();) {
818            Symbol symbol = (Symbol) it.next();
819            array[i++] = symbol;
820        }
821        return array;
822    }
823
824    @Override
825    public String writeToString()
826    {
827        if (_PRINT_FASL_.symbolValue() != NIL && name != null) {
828            StringBuilder sb = new StringBuilder("#.(FIND-PACKAGE \"");
829            sb.append(name);
830            sb.append("\")");
831            return sb.toString();
832        } else
833            return toString();
834    }
835   
836    @Override
837    public String toString() {
838         if (name != null) {
839            StringBuilder sb = new StringBuilder("#<PACKAGE \"");
840            sb.append(name);
841            sb.append("\">");
842            return sb.toString();
843        } else
844            return unreadableString("PACKAGE");
845    }
846}
Note: See TracBrowser for help on using the repository browser.