All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.ow2.fastrmic.Variables Maven / Gradle / Ivy

There is a newer version: 1.0.5
Show newest version
/**
   RMIC.java --
   Copyright (c) 1996, 1997, 1998, 1999, 2001, 2002, 2003, 2004
   Free Software Foundation, Inc.

This file is part of GNU Classpath.

GNU Classpath is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2, or (at your option)
any later version.

GNU Classpath is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
General Public License for more details.

You should have received a copy of the GNU General Public License
along with GNU Classpath; see the file COPYING.  If not, write to the
Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
02111-1307 USA.
 */

package org.ow2.fastrmic;

import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.TreeSet;

class Variables {
    private final TreeSet free = new TreeSet();
    private final HashMap names = new HashMap();
    private final HashSet wides = new HashSet();
    private final HashSet declared = new HashSet();
    private boolean allocated = false;

    /**
     * @return max number of local vars used
     */
    public int max() {
        int max = 0;
        Iterator it = free.iterator();
        while (it.hasNext()) {
            Integer val = (Integer) it.next();
            if (val.intValue() > max) {
                max = val.intValue();
            }
        }
        return max;
    }

    /**
     * @return number or global vars
     */
    public int declaredSize() {
        return declared.size();
    }

    public void declare(Object name) {
        declare(name, 1);
    }

    public void declareWide(Object name) {
        declare(name, 2);
    }

    public void declare(Object name, int size) {
        if (allocated)
            throw new IllegalStateException("cannot declare after allocating");
        if (size != 1 && size != 2)
            throw new IllegalArgumentException("size must be 1 or 2");
        if (names.containsKey(name))
            throw new IllegalStateException("already allocated " + name);

        allocateNew(name, size);
        declared.add(name);
    }

    private int allocateNew(Object name, int size) {
        // total allocation size is first unallocated slot
        int i = free.size() + names.size() + wides.size();
        names.put(name, new Integer(i));
        if (size == 2)
            wides.add(name);
        return i;
    }

    public int allocate(Object name) {
        return allocate(name, 1);
    }

    public int allocateWide(Object name) {
        return allocate(name, 2);
    }

    public int allocate(Object name, int size) {
        allocated = true;
        if (size != 1 && size != 2)
            throw new IllegalArgumentException("size must be 1 or 2");
        if (names.containsKey(name))
            throw new IllegalStateException("already allocated " + name);

        if (size == 2) {
            // look for consecutive free slots
            for (Iterator it = free.iterator(); it.hasNext();) {
                Integer i = (Integer) it.next();
                Integer next = new Integer(i.intValue() + 1);
                if (free.contains(next)) {
                    free.remove(i);
                    free.remove(next);
                    wides.add(name);
                    names.put(name, i);
                    return i.intValue();
                }
            }
        } else if (free.size() > 0) {
            Integer i = (Integer) free.iterator().next();
            free.remove(i);
            names.put(name, i);
            return i.intValue();
        }

        return allocateNew(name, size);
    }

    public int deallocate(Object name) {
        if (!names.containsKey(name))
            throw new IllegalArgumentException("no variable " + name);

        if (declared.contains(name))
            throw new IllegalStateException(name + " can't be deallocated");

        Integer i = (Integer) names.get(name);
        names.remove(name);
        free.add(i);
        if (wides.remove(name)) {
            free.add(new Integer(i.intValue() + 1));
        }
        return i.intValue();
    }

    public int get(Object name) {
        if (!names.containsKey(name))
            throw new IllegalArgumentException("no variable " + name);

        return ((Integer) names.get(name)).intValue();
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy