예제 #1
0
        public IUnsubstitutedBytes toBytes()
        {
            int index = 0;
            IUnsubstitutedBytes tmp = new DynamicUnsubstitutedBytes();
            Queue<ArgumentValue> q = new Queue<ArgumentValue>(arguments.Where(x => (x.result!=null)).Select(x=>(ArgumentValue)x.result));
            foreach (IConditionArgValue v in parent.getCodes(inverted))
            {
                if (v is ArgItemFromArguments)
                {
                    tmp.Combine(arguments[index].toBytes());
            #if DEBUG
                    if (arguments[index].result != null)
                    {
                        throw new Errors.OpcodeFormatError("some opcode has a result for something that shouldn't have");
                    }
            #endif
                    index++;
                }
                else if (v is ArgValueConditionFromArgument)
                {
                    ArgValueConditionFromArgument b = (ArgValueConditionFromArgument)v;
                    if (!(arguments[index].generator is SubstitutedCondition))
                    {
                        throw new Errors.OpcodeFormatError("The arguments field requested a condition, but the opcodes field didn't");
                    }
                    SubstitutedCondition subcond = (SubstitutedCondition)arguments[index].generator;

                    if (b.goTo.getSubstitutionKind() == substitutionType.conditionDestination)
                    {
                        subcond.jumpTo = jumpTo;
                    }
                    else
                    {
                        subcond.jumpTo = b.goTo;
                    }

                    subcond.setInvert(b.invert);

                    tmp.Combine(subcond.toBytes());

                    index++;

                }
                else if (v is Opcode)
                {
                    Opcode b = (Opcode)v;
                    b.setJumpTo(jumpTo);
                    ArgumentValue? returnValue=null;
                    int initalLength = q.Count;
                    IUnsubstitutedBytes bits=b.toBytes(q,ref returnValue);
                    int newLength = q.Count;
                    for (int i=0; i<(initalLength-newLength); i++)
                    {
                        tmp.Combine(arguments[index].generator.toBytes());
                        index++;
                    }
                    tmp.Combine(bits);
                }
                else if (v is IByteable)
                {
                    tmp.Combine(((IByteable)v).toBytes());
                }
            }

            List<Substitution> toRemove = new List<Substitution>();
            List<Substitution> toAdd = new List<Substitution>();

            foreach (Substitution s in tmp.substitutions)
            {
                if (s.type == substitutionType.endCondition)
                {
                    if (s.data == 0)
                    {
                        tmp.WriteSlice(s.position, Writer.toBytes(tmp.Count - s.position - 2));
                        toRemove.Add(s);
                    }
                    else
                    {
                        Substitution d = s;
                        d.data -= 1;
                        toAdd.Add(d);
                        toRemove.Add(s);
                    }
                }
            }
            foreach (Substitution s in toRemove)
            {
                tmp.Complete(s);
            }

            foreach (Substitution s in toAdd)
            {
                tmp.addSubstitution(s);
            }
            return tmp;
        }
예제 #2
0
        public override IUnsubstitutedBytes toBytes()
        {
            Queue<ArgumentValue> argQue = new Queue<ArgumentValue>(argValues);

            DynamicUnsubstitutedBytes tmp = new DynamicUnsubstitutedBytes();
            ArgumentValue? returnValue = this.returnValue;

            foreach (Opcode a in parent.codes)
            {
                tmp.Combine(a.toBytes(argQue, ref returnValue));
            }

            foreach (IPhraseSub s in inter)
            {
                tmp.Combine(s.toBytes());
            }

            foreach (Opcode a in par.getEnd())
            {
                tmp.Combine(a.toBytes(argQue, ref returnValue));
            }

            List<Substitution> subsToRemove = new List<Substitution>();

            foreach (Substitution s in tmp.substitutions)
            {
                if (s.type == substitutionType.NextElse)
                {
                    subsToRemove.Add(s);
                    tmp.WriteSlice(s.position, Writer.toBytes(tmp.Count - s.position - 2));
                }
                if (s.type == substitutionType.BlockStart)
                {
                    subsToRemove.Add(s);
                    tmp.WriteSlice(s.position, Writer.toBytes(-s.position - 2));
                }
            }

            foreach (Substitution s in subsToRemove)
            {
                tmp.Complete(s);
            }

            if (returnValue != null && returnValue.Value.getMode() != addressMode.zero)
            {
                throw new Errors.ReturnTypeViolationError("Attempt to use the return value of " + ToString() + " which has no return value");
            }

            return tmp;
        }