コード例 #1
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
        private static void AddDependingSymb(string symbol, string dependingSymb)
        {
            Dictionary <string, UnresolvedSymbol> unsolvedSymbs;

            if (localScope.isLocalScope)
            {
                unsolvedSymbs = localScope.unsolvedSymbols;
            }
            else
            {
                unsolvedSymbs = unsolvedSymbols;
            }
            if (unsolvedSymbs.ContainsKey(symbol))
            {
                unsolvedSymbs[symbol].DependingList.Add(dependingSymb);
            }
            else
            {
                UnresolvedSymbol unsolved = new UnresolvedSymbol();
                unsolved.DependingList = new List <string>();
                unsolved.DependingList.Add(dependingSymb);
                unsolved.ExprList = new List <ushort>();
                unsolvedSymbs.Add(symbol, unsolved);
            }
        }
コード例 #2
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
        private static void ConstantHandler(Match lineReg)
        {
            string     label = lineReg.Groups["label"].Value;
            string     value = lineReg.Groups["value"].Value;
            ExprResult res   = ResolveExpr(value);

            if (res.undefinedSymbs.Count == 0)
            {
                Symbol symb = new Symbol()
                {
                    Value = res.Result,
                    Type  = res.Type
                };
                AddSymbol(label, symb);
            }
            else
            {
                UnresolvedSymbol unResSymb = new UnresolvedSymbol();
                unResSymb.NbrUndefinedSymb = res.undefinedSymbs.Count;
                unResSymb.DependingList    = new List <string>();
                unResSymb.Expr             = value;
                unResSymb.ExprList         = new List <ushort>();

                foreach (string symb in res.undefinedSymbs)
                {
                    AddDependingSymb(symb, label);
                }

                AddUnsolvedSymbol(label, unResSymb);
            }
        }
コード例 #3
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
        private static void DataByteHandler(string bytesIn)
        {
            string[] bytes = bytesIn.Split(',');
            foreach (string db in bytes)
            {
                string data = db.Trim();
                if (CPUDef.isString(data)) // handle strings
                {
                    data = data.Substring(1, data.Length - 2);
                    foreach (char c in data)
                    {
                        fileOutMemory.Add(Convert.ToByte(c));
                        currentAddr++;
                    }
                }
                else
                {
                    ExprResult res = ResolveExpr(data);
                    if (res.undefinedSymbs.Count == 0)
                    {
                        fileOutMemory.Add((byte)res.Result);
                    }
                    else
                    {
                        fileOutMemory.Add(0);
                        ushort         position = (ushort)(currentAddr - originAddr);
                        UnresolvedExpr expr     = new UnresolvedExpr
                        {
                            Position         = position,
                            Type             = SymbolType.BYTE,
                            addrMode         = CPUDef.AddrModes.NO,
                            NbrUndefinedSymb = res.undefinedSymbs.Count,
                            Expr             = data
                        };

                        unsolvedExprList.Add(position, expr);

                        foreach (string symb in res.undefinedSymbs)
                        {
                            UnresolvedSymbol unResSymb = new UnresolvedSymbol();
                            unResSymb.DependingList = new List <string>();
                            unResSymb.ExprList      = new List <ushort>();
                            unResSymb.ExprList.Add(position);
                            AddUnsolvedSymbol(symb, unResSymb);
                        }
                    }

                    currentAddr++;
                }
            }
        }
コード例 #4
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
        public static void ResolveSymbols()
        {
            List <string> resolved = new List <string>();

            foreach (string symbName in unsolvedSymbols.Keys)
            {
                if (!symbolTable.ContainsKey(symbName))
                {
                    continue;
                }
                UnresolvedSymbol unresSymb = unsolvedSymbols[symbName];
                ResolveSymbolDepsAndExprs(unresSymb);
                resolved.Add(symbName);
            }
            foreach (string symbName in resolved)
            {
                unsolvedSymbols.Remove(symbName);
            }
        }
コード例 #5
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
        private static void ResolveSymbol(string label)
        {
            Dictionary <string, UnresolvedSymbol> unsolvedSymbs;

            if (localScope.isLocalScope)
            {
                unsolvedSymbs = localScope.unsolvedSymbols;
            }
            else
            {
                unsolvedSymbs = unsolvedSymbols;
            }
            if (!unsolvedSymbs.ContainsKey(label))
            {
                return;
            }
            UnresolvedSymbol unresSymb = unsolvedSymbs[label];

            ResolveSymbolDepsAndExprs(unresSymb);
            unsolvedSymbs.Remove(label);
        }
コード例 #6
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
        private static void ResolveSymbolDepsAndExprs(UnresolvedSymbol unresSymb)
        {
            Dictionary <string, UnresolvedSymbol> unsolvedSymbs;

            if (localScope.isLocalScope)
            {
                unsolvedSymbs = localScope.unsolvedSymbols;
            }
            else
            {
                unsolvedSymbs = unsolvedSymbols;
            }
            // resolve depending symbols
            foreach (string dep in unresSymb.DependingList)
            {
                UnresolvedSymbol unresDep = unsolvedSymbs[dep];
                unresDep.NbrUndefinedSymb--;
                if (unresDep.NbrUndefinedSymb <= 0)
                {
                    ExprResult res = ResolveExpr(unresDep.Expr);
                    AddSymbol(dep, new Symbol()
                    {
                        Value = res.Result,
                        Type  = res.Type
                    });
                }
            }
            // resolve expressions
            foreach (ushort expr in unresSymb.ExprList)
            {
                UnresolvedExpr unresExp = unsolvedExprList[expr];
                unresExp.NbrUndefinedSymb--;
                if (unresExp.NbrUndefinedSymb <= 0)
                {
                    ExprResult res = ResolveExpr(unresExp.Expr, unresExp.addrMode);
                    GenerateExprBytes(unresExp, res);
                    unsolvedExprList.Remove(expr);
                }
            }
        }
コード例 #7
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
        private static void AddUnsolvedSymbol(string unsolvedLabel, UnresolvedSymbol unresSymb)
        {
            Dictionary <string, UnresolvedSymbol> unsolvedSymbs;

            if (localScope.isLocalScope)
            {
                unsolvedSymbs = localScope.unsolvedSymbols;
            }
            else
            {
                unsolvedSymbs = unsolvedSymbols;
            }
            if (unsolvedSymbs.ContainsKey(unsolvedLabel))
            {
                UnresolvedSymbol unsolved = unsolvedSymbs[unsolvedLabel];
                foreach (string dep in unresSymb.DependingList)
                {
                    if (!unsolved.DependingList.Contains(dep))
                    {
                        unsolved.DependingList.Add(dep);
                    }
                }
                foreach (ushort expr in unresSymb.ExprList)
                {
                    if (!unsolved.ExprList.Contains(expr))
                    {
                        unsolved.ExprList.Add(expr);
                    }
                }
                if (!string.IsNullOrEmpty(unresSymb.Expr))
                {
                    unsolved.Expr = unresSymb.Expr;
                }
                unsolvedSymbs[unsolvedLabel] = unsolved;
            }
            else
            {
                unsolvedSymbs.Add(unsolvedLabel, unresSymb);
            }
        }
コード例 #8
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
 private static void EndLocalScopeHandler(Match lineReg)
 {
     if (!localScope.isLocalScope)
     {
         AddError(Errors.NO_LOCAL_SCOPE);
         return;
     }
     foreach (string symb in localScope.unsolvedSymbols.Keys)
     {
         if (unsolvedSymbols.ContainsKey(symb))
         {
             UnresolvedSymbol glUnsolvedSymbol    = unsolvedSymbols[symb];
             UnresolvedSymbol localUnsolvedSymbol = localScope.unsolvedSymbols[symb];
             foreach (string dep in localUnsolvedSymbol.DependingList)
             {
                 if (!glUnsolvedSymbol.DependingList.Contains(dep))
                 {
                     glUnsolvedSymbol.DependingList.Add(dep);
                 }
             }
             foreach (ushort expr in localUnsolvedSymbol.ExprList)
             {
                 if (!glUnsolvedSymbol.ExprList.Contains(expr))
                 {
                     glUnsolvedSymbol.ExprList.Add(expr);
                 }
             }
             unsolvedSymbols[symb] = glUnsolvedSymbol;
         }
         else
         {
             UnresolvedSymbol localUnsolvedSymbol = localScope.unsolvedSymbols[symb];
             localUnsolvedSymbol.Expr = null;
             unsolvedSymbols.Add(symb, localUnsolvedSymbol);
         }
     }
     localScope.isLocalScope = false;
     localScope.symbolTable.Clear();
     localScope.unsolvedSymbols.Clear();
 }
コード例 #9
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
        private static void DataWordHandler(string wordsIn)
        {
            string[] words = wordsIn.Split(',');
            foreach (string dw in words)
            {
                string     data = dw.Trim();
                ExprResult res  = ResolveExpr(data);
                if (res.undefinedSymbs.Count == 0)
                {
                    fileOutMemory.AddRange(GetWordBytes((ushort)res.Result));
                }
                else
                {
                    fileOutMemory.AddRange(new byte[2] {
                        0, 0
                    });
                    ushort         position = (ushort)(currentAddr - originAddr);
                    UnresolvedExpr expr     = new UnresolvedExpr
                    {
                        Position         = position,
                        Type             = SymbolType.WORD,
                        addrMode         = CPUDef.AddrModes.NO,
                        NbrUndefinedSymb = res.undefinedSymbs.Count,
                        Expr             = data
                    };

                    unsolvedExprList.Add(position, expr);
                    foreach (string symb in res.undefinedSymbs)
                    {
                        UnresolvedSymbol unResSymb = new UnresolvedSymbol();
                        unResSymb.DependingList = new List <string>();
                        unResSymb.ExprList      = new List <ushort>();
                        unResSymb.ExprList.Add(position);
                        AddUnsolvedSymbol(symb, unResSymb);
                    }
                }
                currentAddr += 2;
            }
        }
コード例 #10
0
ファイル: Assembler.cs プロジェクト: CodewinBzn/WinASM65
        private static void InstructionHandler(Match lineReg)
        {
            string opcode   = lineReg.Groups["opcode"].Value;
            string operands = lineReg.Groups["operands"].Value;

            if (macros.ContainsKey(opcode))
            {
                Match macroReg = Regex.Match($"{opcode} {operands}", CPUDef.macroReg);
                CallMacroHandler(macroReg);
                return;
            }
            string label = lineReg.Groups["label"].Value;

            ushort opcodeAddr = currentAddr;

            opcode = lineReg.Groups["opcode"].Value.ToUpper();
            if (!string.IsNullOrWhiteSpace(label))
            {
                Symbol lSymb = new Symbol {
                    Type = SymbolType.WORD, Value = currentAddr
                };
                AddSymbol(label, lSymb);
            }

            Byte[]           addrModesValues = CPUDef.OPC_TABLE[opcode];
            CPUDef.AddrModes addrMode        = CPUDef.AddrModes.NO;
            List <byte>      instBytes       = new List <byte>();

            CPUDef.InstructionInfo instInfo = new CPUDef.InstructionInfo();
            bool syntaxError = true;

            if (string.IsNullOrWhiteSpace(operands))
            {
                syntaxError = false;
                // 1 byte opcode
                if (Array.Exists(CPUDef.ACC_OPC, opc => opc.Equals(opcode)))
                {
                    addrMode = CPUDef.AddrModes.ACC;
                }
                else
                {
                    addrMode = CPUDef.AddrModes.IMP;
                }
                instInfo = new CPUDef.InstructionInfo {
                    addrMode = addrMode, nbrBytes = 1
                };
                instBytes.Add(addrModesValues[(int)addrMode]);
            }
            else
            {
                string expr = string.Empty;
                // 2 bytes opcode
                if (Array.Exists(CPUDef.REL_OPC, opc => opc.Equals(opcode)))
                {
                    syntaxError = false;
                    expr        = operands;
                    instInfo    = new CPUDef.InstructionInfo {
                        addrMode = CPUDef.AddrModes.REL, nbrBytes = 2
                    };
                }
                else
                {
                    instInfo    = CPUDef.GetInstructionInfo(operands);
                    syntaxError = false;
                    expr        = instInfo.expr;
                }
                if (syntaxError)
                {
                    AddError(Errors.OPERANDS);
                }
                else
                {
                    addrMode = instInfo.addrMode;
                    ExprResult exprRes = ResolveExpr(expr, addrMode);
                    if (exprRes.undefinedSymbs.Count == 0)
                    {
                        // convert to zero page if symbol is a single byte
                        if (CPUDef.isAbsoluteAddr(addrMode) && exprRes.Type == SymbolType.BYTE)
                        {
                            addrMode          = addrMode + 3;
                            instInfo.nbrBytes = 2;
                        }
                        instBytes.Add(addrModesValues[(int)addrMode]);
                        if (instInfo.nbrBytes == 2)
                        {
                            instBytes.Add((byte)exprRes.Result);
                        }
                        else
                        {
                            instBytes.AddRange(GetWordBytes((ushort)exprRes.Result));
                        }
                    }
                    else
                    {
                        instBytes.Add(addrModesValues[(int)addrMode]);
                        SymbolType typeExpr;
                        if (instInfo.nbrBytes == 2)
                        {
                            instBytes.AddRange(new byte[1] {
                                0
                            });
                            typeExpr = SymbolType.BYTE;
                        }
                        else // 3 bytes instr
                        {
                            instBytes.AddRange(new byte[2] {
                                0, 0
                            });
                            typeExpr = SymbolType.WORD;
                        }

                        ushort         position = (ushort)(opcodeAddr - originAddr + 1);
                        UnresolvedExpr exprObj  = new UnresolvedExpr
                        {
                            Position         = position,
                            Type             = typeExpr,
                            addrMode         = addrMode,
                            NbrUndefinedSymb = exprRes.undefinedSymbs.Count,
                            Expr             = expr
                        };
                        unsolvedExprList.Add(position, exprObj);

                        foreach (string symb in exprRes.undefinedSymbs)
                        {
                            UnresolvedSymbol unResSymb = new UnresolvedSymbol();
                            unResSymb.DependingList = new List <string>();
                            unResSymb.ExprList      = new List <ushort>();
                            unResSymb.ExprList.Add(position);
                            AddUnsolvedSymbol(symb, unResSymb);
                        }
                    }
                }
            }
            if (!syntaxError)
            {
                currentAddr += instInfo.nbrBytes;
                fileOutMemory.AddRange(instBytes.ToArray());
                MainConsole.WriteLine($"{opcode} mode {addrMode.ToString()}");
            }
        }