Esempio n. 1
0
        private void TraverseInstructions(GraphBuilderContext context, long entrypoint, IEnumerable <long> knownBlockHeaders)
        {
            var agenda = new Stack <SymbolicProgramState <TInstruction> >();

            foreach (var header in knownBlockHeaders)
            {
                agenda.Push(TransitionResolver.GetInitialState(header));
            }
            agenda.Push(TransitionResolver.GetInitialState(entrypoint));

            while (agenda.Count > 0)
            {
                // Merge the current state with the recorded states.
                var  currentState          = agenda.Pop();
                bool recordedStatesChanged = ApplyStateChange(context, ref currentState);

                // If anything changed, we must invalidate the known successors of the current
                // instruction and (re)visit all its successors.
                if (recordedStatesChanged)
                {
                    var instruction = Instructions.GetCurrentInstruction(currentState);

                    if (context.Result.ContainsInstruction(currentState.ProgramCounter))
                    {
                        context.Result.ClearSuccessors(instruction);
                    }
                    else
                    {
                        context.Result.AddInstruction(instruction);
                    }

                    ResolveAndScheduleSuccessors(context, currentState, instruction, agenda);
                }
            }
        }
Esempio n. 2
0
        /// <inheritdoc />
        protected override IInstructionTraversalResult <TInstruction> CollectInstructions(
            long entrypoint, IEnumerable <long> knownBlockHeaders)
        {
            using var context = new GraphBuilderContext(Architecture);
            long[] blockHeaders = knownBlockHeaders as long[] ?? knownBlockHeaders.ToArray();

            // Perform traversal.
            TraverseInstructions(context, entrypoint, blockHeaders);

            // Register known block headers.
            context.Result.BlockHeaders.Add(entrypoint);
            context.Result.BlockHeaders.UnionWith(blockHeaders);

            // Infer remaining block headers.
            DetermineBlockHeaders(context);

            return(context.Result);
        }
Esempio n. 3
0
        private static bool ApplyStateChange(
            GraphBuilderContext context,
            ref SymbolicProgramState <TInstruction> currentState)
        {
            bool changed;

            if (context.RecordedStates.TryGetValue(currentState.ProgramCounter, out var recordedState))
            {
                // We are revisiting this address, merge program states.
                changed = recordedState.MergeStates(currentState, out currentState);
                if (changed)
                {
                    context.RecordedStates[currentState.ProgramCounter] = currentState;
                }
            }
            else
            {
                // This is a new unvisited address.
                context.RecordedStates.Add(currentState.ProgramCounter, currentState);
                changed = true;
            }

            return(changed);
        }
Esempio n. 4
0
 private void ResolveAndScheduleSuccessors(
     GraphBuilderContext context,
     SymbolicProgramState <TInstruction> currentState,
     in TInstruction instruction,