Advertisement
fastman92

x86 switch scanner

Sep 9th, 2015
203
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 7.33 KB | None | 0 0
  1. #include <idc.idc>
  2. #define TRUE 1
  3. #define FALSE 0
  4. #define true 1
  5. #define false 0
  6. #define NULL 0
  7.  
  8. /*
  9.     Project name: x86 switch scanner
  10.  
  11.     Author: fastman92
  12.    
  13.     Description: this script finds all switches and displays a list of cases for each.
  14. */
  15.  
  16.  
  17. static IsSwitchJmp(ea)
  18. {  
  19.     if(GetMnem(ea) != "jmp" || GetOpType(ea, 0) != o_mem)
  20.         return false;
  21.    
  22.     auto op = GetOpnd(ea, 0);
  23.    
  24.     auto last = substr(op, strlen(op) - 3, -1);
  25.    
  26.     return last == "*4]";
  27. }
  28.  
  29. static main()
  30. {
  31.     Message("Start of x86 switch scanner by fastman92\n");
  32.  
  33.     auto seg, loc;
  34.  
  35.     Message("========================================\n");
  36.    
  37.     seg = FirstSeg();   // Get address pointed by a first segment
  38.    
  39.     auto PointerTable;
  40.     auto XlatTable;
  41.     auto DefaultLocation;
  42.     auto NumberOfCases;
  43.     auto LowestValue;
  44.     auto NumberOfCasesSet;
  45.    
  46.     auto locPrev;
  47.     auto cmd;
  48.     auto j;
  49.     auto destination;
  50.    
  51.      
  52.     while(seg != BADADDR )
  53.     {  
  54.         Message("----------------------------------------\n");
  55.  
  56.         loc = SegStart(seg);
  57.        
  58.         Message("Segment %s\n", SegName(seg));
  59.  
  60.         // loc = 0x7AA341;
  61.  
  62.         while(loc != BADADDR && loc < SegEnd(seg))
  63.         {                          
  64.             if(isCode(GetFlags(loc)))
  65.             {
  66.                 auto mnem = GetMnem(loc);
  67.            
  68.                 if(IsSwitchJmp(loc))
  69.                 {
  70.                     if(Word(loc) == 0x24FF)
  71.                     {
  72.                         LowestValue = 0;
  73.                         DefaultLocation = 0;
  74.                         NumberOfCases = 0;
  75.                         NumberOfCasesSet = false;
  76.                        
  77.                         PointerTable = GetOperandValue(loc, 0);
  78.                         auto switchReg = (Byte(loc + 2) >> 3) & 7;
  79.                        
  80.                         XlatTable = NULL;
  81.                         // Message("Instruction 0x%X Disasm: %s\n", loc, GetDisasm(loc));
  82.                        
  83.                         auto state = 0;
  84.                        
  85.                         locPrev = loc;
  86.                        
  87.                         auto i = 0;
  88.                        
  89.                         while(true)
  90.                         {
  91.                             i++;
  92.                             // Message("Address 0x%X lowest value: %d\n", locPrev, LowestValue);
  93.                            
  94.                             locPrev = PrevHead(locPrev, 0);
  95.                             mnem = GetMnem(locPrev);
  96.                            
  97.                             if(DefaultLocation == 0
  98.                                 && mnem == "movzx"
  99.                                 && GetOpType(locPrev, 0) == o_reg
  100.                                 && GetOperandValue(locPrev, 0) == switchReg
  101.                                 )
  102.                             {
  103.                                 XlatTable = GetOperandValue(locPrev, 1);
  104.                                 switchReg = Byte(locPrev + 2) & 7;
  105.                                 // Message("Xlat = 0x%X\n", XlatTable);
  106.                                
  107.                                 // Message("Instruction 0x%X Disasm: %s\n", locPrev, GetDisasm(locPrev));
  108.                             }
  109.                             else if(mnem == "ja")
  110.                             {
  111.                                 cmd = cmd = DecodeInstruction(locPrev);
  112.                                 DefaultLocation = cmd.Op0.addr;                                                
  113.                             }
  114.                             else if(
  115.                                 !NumberOfCasesSet &&
  116.                                 mnem == "cmp"
  117.                                 && GetOpType(locPrev, 0) == o_reg
  118.                                 && GetOperandValue(locPrev, 0) == switchReg
  119.                                 && GetOpType(locPrev, 1) == o_imm
  120.                                 )
  121.                             {
  122.                                 NumberOfCasesSet = true;
  123.                                 NumberOfCases = GetOperandValue(locPrev, 1) + 1;
  124.                             }
  125.                             else if(
  126.                                 !NumberOfCasesSet &&
  127.                                 mnem == "cmp"
  128.                                 && GetOpType(locPrev, 0) == o_reg
  129.                                 && GetOperandValue(locPrev, 0) == switchReg
  130.                                 && GetOpType(locPrev, 1) == o_reg
  131.                                 )
  132.                             {
  133.                                 auto registerForComparison = GetOperandValue(locPrev, 1);
  134.                                
  135.                                 auto locPrevPrev = locPrev;
  136.                                
  137.                                
  138.                                 while(true)
  139.                                 {
  140.                                     locPrevPrev = PrevHead(locPrevPrev, 0);
  141.                                     auto xMnem = GetMnem(locPrevPrev);
  142.                                                                        
  143.                                    
  144.                                     if(xMnem == "mov"
  145.                                         && GetOpType(locPrevPrev, 0) == o_reg
  146.                                         && GetOperandValue(locPrevPrev, 0) == registerForComparison
  147.                                         && GetOpType(locPrevPrev, 1) == o_imm
  148.                                         )
  149.                                     {
  150.                                         NumberOfCases = GetOperandValue(locPrevPrev, 1) + 1;                                                                       
  151.                                         break;
  152.                                     }
  153.                                     else if(xMnem == "pop"
  154.                                         && GetOpType(locPrevPrev, 0) == o_reg
  155.                                         && GetOperandValue(locPrevPrev, 0) == registerForComparison
  156.                                         )
  157.                                     {
  158.                                        
  159.                                        
  160.                                         while(true)
  161.                                         {
  162.                                             if(GetMnem(locPrevPrev) == "push")
  163.                                             {
  164.                                                 if(GetOpType(locPrevPrev, 0) == o_imm)
  165.                                                     NumberOfCases = GetOperandValue(locPrevPrev, 0) + 1;
  166.                                                 else
  167.                                                     NumberOfCases = -1;                                            
  168.                                                
  169.                                                 break;
  170.                                             }
  171.                                            
  172.                                             locPrevPrev = PrevHead(locPrevPrev, 0);
  173.                                         }
  174.                                        
  175.                                         break;
  176.                                     }
  177.  
  178.                                    
  179.                                 }
  180.                             }
  181.                            
  182.                             else if(mnem == "add"
  183.                                 && GetOpType(locPrev, 0) == o_reg
  184.                                 && GetOperandValue(locPrev, 0) == switchReg
  185.                                 && GetOpType(locPrev, 1) == o_imm          
  186.                                 )
  187.                             {
  188.                                 LowestValue = -GetOperandValue(locPrev, 1);
  189.                                 break;
  190.                             }
  191.                             else if(mnem == "sub"
  192.                                 && GetOpType(locPrev, 0) == o_reg
  193.                                 && GetOperandValue(locPrev, 0) == switchReg
  194.                                 && GetOpType(locPrev, 1) == o_imm          
  195.                                 )
  196.                             {
  197.                                 LowestValue = GetOperandValue(locPrev, 1);
  198.                                 break;
  199.                             }
  200.                             else if(mnem == "dec"
  201.                                 && GetOpType(locPrev, 0) == o_reg
  202.                                 && GetOperandValue(locPrev, 0) == switchReg
  203.                                 )
  204.                             {
  205.                                 LowestValue = 1;
  206.                                 break;
  207.                             }
  208.                             else if(mnem == "inc"
  209.                                 && GetOpType(locPrev, 0) == o_reg
  210.                                 && GetOperandValue(locPrev, 0) == switchReg
  211.                                 )
  212.                             {
  213.                                 LowestValue = -1;
  214.                                 break;
  215.                             }
  216.                             else if(
  217.                                 mnem == "lea"
  218.                                 && GetOpType(locPrev, 0) == o_reg
  219.                                 && GetOperandValue(locPrev, 0) == switchReg
  220.                             )
  221.                             {
  222.                                 if(GetOpType(locPrev, 1) == o_displ)
  223.                                     LowestValue = -GetOperandValue(locPrev, 1);
  224.                                
  225.                                 break;
  226.                             }                          
  227.                             else if(
  228.                                 (mnem == "movzx" || mnem == "movsx" || mnem == "mov" || mnem == "and")
  229.                                 && GetOpType(locPrev, 0) == o_reg
  230.                                 && GetOperandValue(locPrev, 0) == switchReg
  231.                                 )
  232.                                 break;
  233.                             else if(mnem == "call")
  234.                                 break;
  235.                            
  236.                             // if(i > 3)
  237.                             //  break;
  238.                            
  239.                         }
  240.                        
  241.                         Message("\nSwitch 0x%X:\n", loc);
  242.                         Message("\tXLAT table: 0x%X\n", XlatTable);
  243.                         Message("\tPointer table: 0x%X\n", PointerTable);
  244.                         Message("\tDefault case: 0x%X\n", DefaultLocation);
  245.                        
  246.                         Message("\tNumber of cases: %d\n", NumberOfCases);
  247.                         Message("\tLowest case: %d\n", LowestValue);
  248.                        
  249.                         Message("\tCases:\n");
  250.                        
  251.                         if(XlatTable)
  252.                         {
  253.                             for(j = 0; j < NumberOfCases; j++)
  254.                             {
  255.                                 destination = Dword(PointerTable + Byte(XlatTable + j) * 4);
  256.                                
  257.                                
  258.                                 if(destination != DefaultLocation)                             
  259.                                     Message("\t\t%d - 0x%X\n", LowestValue + j, destination);
  260.                                
  261.                                 /*
  262.                                 if(destination == DefaultLocation)
  263.                                     Message(" (default)");
  264.                                 */
  265.                                
  266.                             }                          
  267.                         }
  268.                         else
  269.                         {
  270.                             for(j = 0; j < NumberOfCases; j++)
  271.                             {
  272.                                 destination = Dword(PointerTable + j * 4);
  273.                                
  274.                                 if(destination != DefaultLocation)
  275.                                     Message("\t\t%d - 0x%X\n", LowestValue + j, destination);
  276.                                
  277.                                 /*
  278.                                 if(destination == DefaultLocation)
  279.                                     Message(" (default)");
  280.                                 */
  281.                                
  282.                             }
  283.                         }
  284.                        
  285.                     }
  286.                     else
  287.                     {
  288.                         Message("Don't know how to process Instruction 0x%X Disasm: %s\n", loc, GetDisasm(loc));
  289.                     }
  290.                    
  291.                 }
  292.             }
  293.            
  294.             // break;
  295.            
  296.             loc = NextHead(loc, BADADDR);
  297.         }
  298.        
  299.         // break;
  300.      
  301.         seg = NextSeg(seg);     // get address of the next segment
  302.     }
  303. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement