001/* A simple integer arithmetic logic unit. 002 003 Copyright (c) 1997-2014 The Regents of the University of California. 004 All rights reserved. 005 Permission is hereby granted, without written agreement and without 006 license or royalty fees, to use, copy, modify, and distribute this 007 software and its documentation for any purpose, provided that the above 008 copyright notice and the following two paragraphs appear in all copies 009 of this software. 010 011 IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY 012 FOR DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES 013 ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF 014 THE UNIVERSITY OF CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF 015 SUCH DAMAGE. 016 017 THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, 018 INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 019 MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE 020 PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND THE UNIVERSITY OF 021 CALIFORNIA HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT, UPDATES, 022 ENHANCEMENTS, OR MODIFICATIONS. 023 024 PT_COPYRIGHT_VERSION_2 025 COPYRIGHTENDKEY 026 027 */ 028package ptolemy.actor.lib.tutorial; 029 030import ptolemy.actor.TypedAtomicActor; 031import ptolemy.actor.TypedIOPort; 032import ptolemy.data.IntToken; 033import ptolemy.data.Token; 034import ptolemy.data.type.BaseType; 035import ptolemy.kernel.CompositeEntity; 036import ptolemy.kernel.util.IllegalActionException; 037import ptolemy.kernel.util.NameDuplicationException; 038import ptolemy.kernel.util.Workspace; 039 040/////////////////////////////////////////////////////////////////// 041//// SimpleALU 042 043/** 044 <p> 045 A simple integer arithmetic logic unit. 046 </p> 047 048 @author Man-Kit Leung 049 @version $Id$ 050 @since Ptolemy II 6.0.2 051 @Pt.ProposedRating Red (mankit) 052 @Pt.AcceptedRating Red (mankit) 053 */ 054public class SimpleALU extends TypedAtomicActor { 055 /** Construct an actor in the specified container with the specified 056 * name. 057 * @param container The container. 058 * @param name The name of this adder within the container. 059 * @exception IllegalActionException If the actor cannot be contained 060 * by the proposed container. 061 * @exception NameDuplicationException If the name coincides with 062 * an actor already in the container. 063 */ 064 public SimpleALU(CompositeEntity container, String name) 065 throws IllegalActionException, NameDuplicationException { 066 super(container, name); 067 A = new TypedIOPort(this, "A", true, false); 068 A.setTypeEquals(BaseType.INT); 069 B = new TypedIOPort(this, "B", true, false); 070 B.setTypeEquals(BaseType.INT); 071 072 operation = new TypedIOPort(this, "operation", true, false); 073 operation.setTypeEquals(BaseType.INT); 074 075 output = new TypedIOPort(this, "output", false, true); 076 output.setTypeEquals(BaseType.INT); 077 078 } 079 080 /////////////////////////////////////////////////////////////////// 081 //// ports and parameters //// 082 083 /** Input port for the first operand. The port type is integer. 084 */ 085 public TypedIOPort A; 086 087 /** Input port for the second operand. The port type is integer. 088 */ 089 public TypedIOPort B; 090 091 /** Input port for the operation code. The port type is integer. 092 * The value of the input tokens should not exceed the number of 093 * operations supported. 094 */ 095 public TypedIOPort operation; 096 097 /** Output port. The type is inferred from the connections. 098 */ 099 public TypedIOPort output; 100 101 /////////////////////////////////////////////////////////////////// 102 //// public methods //// 103 104 /** Override the base class to set type constraints. 105 * @param workspace The workspace for the new object. 106 * @return A new instance of SimpleALU. 107 * @exception CloneNotSupportedException If a derived class contains 108 * an attribute that cannot be cloned. 109 */ 110 @Override 111 public Object clone(Workspace workspace) throws CloneNotSupportedException { 112 SimpleALU newObject = (SimpleALU) super.clone(workspace); 113 newObject.A.setTypeEquals(BaseType.INT); 114 newObject.B.setTypeEquals(BaseType.INT); 115 newObject.operation.setTypeEquals(BaseType.INT); 116 return newObject; 117 } 118 119 /** If there is at least one token on each of the input ports, the 120 * first token from each port is consumed. The value of the token 121 * from the operation input port determines which operation will be 122 * perform on the tokens from input port A and B. The opcode is 123 * defined as follow: 124 * 0 - NOP 125 * 1 - Addition (A + B) 126 * 2 - Subtraction (A - B) 127 * 3 - Multiplication (A * B) 128 * 4 - Division (A / B) 129 * @exception IllegalActionException If the input operation code 130 * is not supported. 131 */ 132 @Override 133 public void fire() throws IllegalActionException { 134 super.fire(); 135 Token result = null; 136 137 if (A.hasToken(0) && B.hasToken(0) && operation.hasToken(0)) { 138 int opcode = ((IntToken) operation.get(0)).intValue(); 139 IntToken tokenA = (IntToken) A.get(0); 140 IntToken tokenB = (IntToken) B.get(0); 141 142 switch (opcode) { 143 case 0: // NOP 144 result = IntToken.ZERO; 145 break; 146 case 1: // addition 147 result = tokenA.add(tokenB); 148 break; 149 case 2: // subtraction 150 result = tokenA.subtract(tokenB); 151 break; 152 case 3: // multiplication 153 result = tokenA.multiply(tokenB); 154 break; 155 case 4: // division 156 result = tokenA.divide(tokenB); 157 break; 158 default: 159 throw new IllegalActionException(this, 160 "Unsupported operation code: " + opcode + ".\n"); 161 } 162 } 163 output.send(0, result); 164 } 165}