ReactOS 0.4.15-dev-6656-gbbb33a6
kdb_expr.c File Reference
#include <ntoskrnl.h>
#include "kdb.h"
#include "debug.h"
Include dependency graph for kdb_expr.c:

Go to the source code of this file.

Classes

struct  _RPN_OP
 
struct  _RPN_STACK
 

Macros

#define NDEBUG
 
#define stricmp   _stricmp
 
#define RTL_FIELD_SIZE(type, field)   (sizeof(((type *)0)->field))
 
#define CONST_STRCPY(dst, src)    do { if ((dst)) { memcpy(dst, src, sizeof(src)); } } while (0);
 
#define RPN_OP_STACK_SIZE   256
 
#define RPN_VALUE_STACK_SIZE   256
 

Typedefs

typedef enum _RPN_OP_TYPE RPN_OP_TYPE
 
typedef ULONGLONG(* RPN_BINARY_OPERATOR) (ULONGLONG a, ULONGLONG b)
 
typedef struct _RPN_OP RPN_OP
 
typedef struct _RPN_OPPRPN_OP
 
typedef struct _RPN_STACK RPN_STACK
 
typedef struct _RPN_STACKPRPN_STACK
 

Enumerations

enum  _RPN_OP_TYPE {
  RpnOpNop , RpnOpBinaryOperator , RpnOpUnaryOperator , RpnOpImmediate ,
  RpnOpRegister , RpnOpDereference
}
 

Functions

ULONGLONG RpnBinaryOperatorAdd (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorSub (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorMul (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorDiv (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorMod (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorEquals (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorNotEquals (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorLessThan (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorLessThanOrEquals (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorGreaterThan (ULONGLONG a, ULONGLONG b)
 
ULONGLONG RpnBinaryOperatorGreaterThanOrEquals (ULONGLONG a, ULONGLONG b)
 
static VOID RpnpClearStack (OUT PRPN_STACK Stack)
 Clears the given RPN stack.
 
static BOOLEAN RpnpPushStack (IN OUT PRPN_STACK Stack, IN PRPN_OP Op)
 Pushes an RPN_OP onto the stack.
 
static BOOLEAN RpnpPopStack (IN OUT PRPN_STACK Stack, OUT PRPN_OP Op OPTIONAL)
 Pops the top op from the stack.
 
static BOOLEAN RpnpTopStack (IN PRPN_STACK Stack, OUT PRPN_OP Op)
 Gets the top op from the stack (not popping it)
 
static BOOLEAN RpnpParseExpression (IN PRPN_STACK Stack, IN PCHAR Expression, OUT PCHAR *End OPTIONAL, IN ULONG CharacterOffset, OUT PLONG ErrOffset OPTIONAL, OUT PCHAR ErrMsg OPTIONAL)
 Parses an expression.
 
static BOOLEAN RpnpEvaluateStack (IN PRPN_STACK Stack, IN PKDB_KTRAP_FRAME TrapFrame, OUT PULONGLONG Result, OUT PLONG ErrOffset OPTIONAL, OUT PCHAR ErrMsg OPTIONAL)
 Evaluates the RPN op stack and returns the result.
 
BOOLEAN KdbpRpnEvaluateExpression (IN PCHAR Expression, IN PKDB_KTRAP_FRAME TrapFrame, OUT PULONGLONG Result, OUT PLONG ErrOffset OPTIONAL, OUT PCHAR ErrMsg OPTIONAL)
 Evaluates the given expression.
 
PVOID KdbpRpnParseExpression (IN PCHAR Expression, OUT PLONG ErrOffset OPTIONAL, OUT PCHAR ErrMsg OPTIONAL)
 Parses the given expression and returns a "handle" to it.
 
BOOLEAN KdbpRpnEvaluateParsedExpression (IN PVOID Expression, IN PKDB_KTRAP_FRAME TrapFrame, OUT PULONGLONG Result, OUT PLONG ErrOffset OPTIONAL, OUT PCHAR ErrMsg OPTIONAL)
 Evaluates the given expression and returns the result.
 

Variables

struct {
   ULONG   Size
 
   ULONG   Sp
 
   RPN_OP   Ops [RPN_OP_STACK_SIZE]
 
RpnStack
 
struct {
   PCHAR   Name
 
   UCHAR   Offset
 
   UCHAR   Size
 
RegisterToTrapFrame []
 
static const INT RegisterToTrapFrameCount = sizeof (RegisterToTrapFrame) / sizeof (RegisterToTrapFrame[0])
 

Macro Definition Documentation

◆ CONST_STRCPY

#define CONST_STRCPY (   dst,
  src 
)     do { if ((dst)) { memcpy(dst, src, sizeof(src)); } } while (0);

Definition at line 89 of file kdb_expr.c.

◆ NDEBUG

#define NDEBUG

Definition at line 39 of file kdb_expr.c.

◆ RPN_OP_STACK_SIZE

#define RPN_OP_STACK_SIZE   256

Definition at line 92 of file kdb_expr.c.

◆ RPN_VALUE_STACK_SIZE

#define RPN_VALUE_STACK_SIZE   256

Definition at line 93 of file kdb_expr.c.

◆ RTL_FIELD_SIZE

#define RTL_FIELD_SIZE (   type,
  field 
)    (sizeof(((type *)0)->field))

Definition at line 86 of file kdb_expr.c.

◆ stricmp

#define stricmp   _stricmp

Definition at line 83 of file kdb_expr.c.

Typedef Documentation

◆ PRPN_OP

typedef struct _RPN_OP * PRPN_OP

◆ PRPN_STACK

◆ RPN_BINARY_OPERATOR

typedef ULONGLONG(* RPN_BINARY_OPERATOR) (ULONGLONG a, ULONGLONG b)

Definition at line 53 of file kdb_expr.c.

◆ RPN_OP

◆ RPN_OP_TYPE

◆ RPN_STACK

Enumeration Type Documentation

◆ _RPN_OP_TYPE

Enumerator
RpnOpNop 
RpnOpBinaryOperator 
RpnOpUnaryOperator 
RpnOpImmediate 
RpnOpRegister 
RpnOpDereference 

Definition at line 43 of file kdb_expr.c.

44{
enum _RPN_OP_TYPE RPN_OP_TYPE
@ RpnOpNop
Definition: kdb_expr.c:45
@ RpnOpBinaryOperator
Definition: kdb_expr.c:46
@ RpnOpRegister
Definition: kdb_expr.c:49
@ RpnOpDereference
Definition: kdb_expr.c:50
@ RpnOpUnaryOperator
Definition: kdb_expr.c:47
@ RpnOpImmediate
Definition: kdb_expr.c:48

Function Documentation

◆ KdbpRpnEvaluateExpression()

BOOLEAN KdbpRpnEvaluateExpression ( IN PCHAR  Expression,
IN PKDB_KTRAP_FRAME  TrapFrame,
OUT PULONGLONG  Result,
OUT PLONG ErrOffset  OPTIONAL,
OUT PCHAR ErrMsg  OPTIONAL 
)

Evaluates the given expression.

Parameters
ExpressionExpression to evaluate.
TrapFrameRegister values.
ResultVariable which receives the result on success.
ErrOffsetVariable which receives character offset on parse error (-1 on other errors)
ErrMsgBuffer which receives an error message on failure (128 bytes)
Return values
TRUESuccess.
FALSEFailure.

Definition at line 1106 of file kdb_expr.c.

1112{
1114
1116 ASSERT(TrapFrame);
1117 ASSERT(Result);
1118
1119 /* Clear the stack and parse the expression */
1121 if (!RpnpParseExpression(Stack, Expression, NULL, 0, ErrOffset, ErrMsg))
1122 return FALSE;
1123
1124#ifdef DEBUG_RPN
1125 RpnpDumpStack(Stack);
1126#endif
1127
1128 /* Evaluate the stack */
1129 if (!RpnpEvaluateStack(Stack, TrapFrame, Result, ErrOffset, ErrMsg))
1130 return FALSE;
1131
1132 return TRUE;
1133}
PCWSTR Expression
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
static BOOLEAN RpnpParseExpression(IN PRPN_STACK Stack, IN PCHAR Expression, OUT PCHAR *End OPTIONAL, IN ULONG CharacterOffset, OUT PLONG ErrOffset OPTIONAL, OUT PCHAR ErrMsg OPTIONAL)
Parses an expression.
Definition: kdb_expr.c:426
static VOID RpnpClearStack(OUT PRPN_STACK Stack)
Clears the given RPN stack.
Definition: kdb_expr.c:329
static struct @1796 RpnStack
struct _RPN_STACK * PRPN_STACK
static BOOLEAN RpnpEvaluateStack(IN PRPN_STACK Stack, IN PKDB_KTRAP_FRAME TrapFrame, OUT PULONGLONG Result, OUT PLONG ErrOffset OPTIONAL, OUT PCHAR ErrMsg OPTIONAL)
Evaluates the RPN op stack and returns the result.
Definition: kdb_expr.c:897
#define ASSERT(a)
Definition: mode.c:44
_In_ WDFREQUEST _In_ PIO_STACK_LOCATION Stack
Definition: wdfrequest.h:639
_At_(*)(_In_ PWSK_CLIENT Client, _In_opt_ PUNICODE_STRING NodeName, _In_opt_ PUNICODE_STRING ServiceName, _In_opt_ ULONG NameSpace, _In_opt_ GUID *Provider, _In_opt_ PADDRINFOEXW Hints, _Outptr_ PADDRINFOEXW *Result, _In_opt_ PEPROCESS OwningProcess, _In_opt_ PETHREAD OwningThread, _Inout_ PIRP Irp Result)(Mem)) NTSTATUS(WSKAPI *PFN_WSK_GET_ADDRESS_INFO
Definition: wsk.h:409

Referenced by KdbpEvaluateExpression().

◆ KdbpRpnEvaluateParsedExpression()

BOOLEAN KdbpRpnEvaluateParsedExpression ( IN PVOID  Expression,
IN PKDB_KTRAP_FRAME  TrapFrame,
OUT PULONGLONG  Result,
OUT PLONG ErrOffset  OPTIONAL,
OUT PCHAR ErrMsg  OPTIONAL 
)

Evaluates the given expression and returns the result.

Parameters
ExpressionExpression "handle" returned by KdbpRpnParseExpression.
TrapFrameRegister values.
ResultVariable which receives the result on success.
ErrOffsetVariable which receives character offset on parse error (-1 on other errors)
ErrMsgBuffer which receives an error message on failure (128 bytes)
Returns
"Handle" for the expression, NULL on failure.
See also
KdbpRpnParseExpression

Definition at line 1200 of file kdb_expr.c.

1206{
1208
1210 ASSERT(TrapFrame);
1211 ASSERT(Result);
1212
1213 /* Evaluate the stack */
1214 return RpnpEvaluateStack(Stack, TrapFrame, Result, ErrOffset, ErrMsg);
1215}

Referenced by KdbEnterDebuggerException().

◆ KdbpRpnParseExpression()

PVOID KdbpRpnParseExpression ( IN PCHAR  Expression,
OUT PLONG ErrOffset  OPTIONAL,
OUT PCHAR ErrMsg  OPTIONAL 
)

Parses the given expression and returns a "handle" to it.

Parameters
ExpressionExpression to evaluate.
ErrOffsetVariable which receives character offset on parse error (-1 on other errors)
ErrMsgBuffer which receives an error message on failure (128 bytes)
Returns
"Handle" for the expression, NULL on failure.
See also
KdbpRpnEvaluateExpression

Definition at line 1146 of file kdb_expr.c.

1150{
1151 LONG Size;
1153 PRPN_STACK NewStack;
1154
1156
1157 /* Clear the stack and parse the expression */
1159 if (!RpnpParseExpression(Stack, Expression, NULL, 0, ErrOffset, ErrMsg))
1160 return FALSE;
1161
1162#ifdef DEBUG_RPN
1163 RpnpDumpStack(Stack);
1164#endif
1165
1166 /* Duplicate the stack and return a pointer/handle to it */
1167 ASSERT(Stack->Sp >= 1);
1168 Size = sizeof (RPN_STACK) + (RTL_FIELD_SIZE(RPN_STACK, Ops[0]) * (Stack->Sp - 1));
1170
1171 if (!NewStack)
1172 {
1173 CONST_STRCPY(ErrMsg, "Out of memory");
1174
1175 if (ErrOffset)
1176 *ErrOffset = -1;
1177
1178 return NULL;
1179 }
1180
1181 memcpy(NewStack, Stack, Size);
1182 NewStack->Size = NewStack->Sp;
1183
1184 return NewStack;
1185}
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
#define NonPagedPool
Definition: env_spec_w32.h:307
#define RTL_FIELD_SIZE(type, field)
Definition: kdb_expr.c:86
RPN_OP Ops[RPN_OP_STACK_SIZE]
Definition: kdb_expr.c:100
struct _RPN_STACK RPN_STACK
ULONG Size
Definition: kdb_expr.c:98
#define CONST_STRCPY(dst, src)
Definition: kdb_expr.c:89
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
long LONG
Definition: pedump.c:60
ULONG Size
Definition: kdb_expr.c:76
ULONG Sp
Definition: kdb_expr.c:77
#define TAG_KDBG
Definition: tag.h:38
_Must_inspect_result_ _In_ WDFDEVICE _In_ PWDF_DEVICE_PROPERTY_DATA _In_ DEVPROPTYPE _In_ ULONG Size
Definition: wdfdevice.h:4533

Referenced by KdbpInsertBreakPoint().

◆ RpnBinaryOperatorAdd()

ULONGLONG RpnBinaryOperatorAdd ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 160 of file kdb_expr.c.

163{
164 return a + b;
165}
GLboolean GLboolean GLboolean GLboolean a
Definition: glext.h:6204
#define b
Definition: ke_i.h:79

Referenced by RpnpParseExpression().

◆ RpnBinaryOperatorDiv()

ULONGLONG RpnBinaryOperatorDiv ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 184 of file kdb_expr.c.

187{
188 return a / b;
189}

Referenced by RpnpEvaluateStack(), and RpnpParseExpression().

◆ RpnBinaryOperatorEquals()

ULONGLONG RpnBinaryOperatorEquals ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 200 of file kdb_expr.c.

203{
204 return (a == b);
205}
GLboolean GLboolean GLboolean b
Definition: glext.h:6204

Referenced by RpnpParseExpression().

◆ RpnBinaryOperatorGreaterThan()

ULONGLONG RpnBinaryOperatorGreaterThan ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 232 of file kdb_expr.c.

235{
236 return (a > b);
237}

Referenced by RpnpParseExpression().

◆ RpnBinaryOperatorGreaterThanOrEquals()

ULONGLONG RpnBinaryOperatorGreaterThanOrEquals ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 240 of file kdb_expr.c.

243{
244 return (a >= b);
245}

Referenced by RpnpParseExpression().

◆ RpnBinaryOperatorLessThan()

ULONGLONG RpnBinaryOperatorLessThan ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 216 of file kdb_expr.c.

219{
220 return (a < b);
221}

Referenced by RpnpParseExpression().

◆ RpnBinaryOperatorLessThanOrEquals()

ULONGLONG RpnBinaryOperatorLessThanOrEquals ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 224 of file kdb_expr.c.

227{
228 return (a <= b);
229}

Referenced by RpnpParseExpression().

◆ RpnBinaryOperatorMod()

ULONGLONG RpnBinaryOperatorMod ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 192 of file kdb_expr.c.

195{
196 return a % b;
197}

Referenced by RpnpParseExpression().

◆ RpnBinaryOperatorMul()

ULONGLONG RpnBinaryOperatorMul ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 176 of file kdb_expr.c.

179{
180 return a * b;
181}

Referenced by RpnpParseExpression().

◆ RpnBinaryOperatorNotEquals()

ULONGLONG RpnBinaryOperatorNotEquals ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 208 of file kdb_expr.c.

211{
212 return (a != b);
213}

Referenced by RpnpParseExpression().

◆ RpnBinaryOperatorSub()

ULONGLONG RpnBinaryOperatorSub ( ULONGLONG  a,
ULONGLONG  b 
)

Definition at line 168 of file kdb_expr.c.

171{
172 return a - b;
173}

Referenced by RpnpParseExpression().

◆ RpnpClearStack()

static VOID RpnpClearStack ( OUT PRPN_STACK  Stack)
static

Clears the given RPN stack.

Parameters
StackPointer to a RPN_STACK structure.

Definition at line 329 of file kdb_expr.c.

331{
332 ASSERT(Stack);
333 Stack->Sp = 0;
334}

Referenced by KdbpRpnEvaluateExpression(), and KdbpRpnParseExpression().

◆ RpnpEvaluateStack()

static BOOLEAN RpnpEvaluateStack ( IN PRPN_STACK  Stack,
IN PKDB_KTRAP_FRAME  TrapFrame,
OUT PULONGLONG  Result,
OUT PLONG ErrOffset  OPTIONAL,
OUT PCHAR ErrMsg  OPTIONAL 
)
static

Evaluates the RPN op stack and returns the result.

Parameters
StackPointer to a RPN_STACK structure.
TrapFrameRegister values.
ResultPointer to an ULONG to store the result into.
ErrOffsetOn failure this is set to the character offset at which the error occoured.
ErrMsgBuffer which receives an error message on failure (128 bytes)
Return values
TRUESuccess.
FALSEFailure.

Definition at line 897 of file kdb_expr.c.

903{
905 ULONG ValueStackPointer = 0;
906 ULONG index;
907 ULONGLONG ull;
908 ULONG ul;
909 USHORT us;
910 UCHAR uc;
911 PVOID p;
912 BOOLEAN Ok;
913#ifdef DEBUG_RPN
914 ULONG ValueStackPointerMax = 0;
915#endif
916
917 ASSERT(Stack);
918 ASSERT(TrapFrame);
919 ASSERT(Result);
920
921 for (index = 0; index < Stack->Sp; index++)
922 {
923 PRPN_OP Op = Stack->Ops + index;
924
925#ifdef DEBUG_RPN
926 ValueStackPointerMax = max(ValueStackPointerMax, ValueStackPointer);
927#endif
928
929 switch (Op->Type)
930 {
931 case RpnOpNop:
932 /* No operation */
933 break;
934
935 case RpnOpImmediate:
936 if (ValueStackPointer == RPN_VALUE_STACK_SIZE)
937 {
938 CONST_STRCPY(ErrMsg, "Value stack overflow");
939
940 if (ErrOffset)
941 *ErrOffset = -1;
942
943 return FALSE;
944 }
945
946 ValueStack[ValueStackPointer++] = Op->Data.Immediate;
947 break;
948
949 case RpnOpRegister:
950 if (ValueStackPointer == RPN_VALUE_STACK_SIZE)
951 {
952 CONST_STRCPY(ErrMsg, "Value stack overflow");
953
954 if (ErrOffset)
955 *ErrOffset = -1;
956
957 return FALSE;
958 }
959
960 ul = Op->Data.Register;
961 p = (PVOID)((ULONG_PTR)TrapFrame + RegisterToTrapFrame[ul].Offset);
962
963 switch (RegisterToTrapFrame[ul].Size)
964 {
965 case 1: ull = (ULONGLONG)(*(PUCHAR)p); break;
966 case 2: ull = (ULONGLONG)(*(PUSHORT)p); break;
967 case 4: ull = (ULONGLONG)(*(PULONG)p); break;
968 case 8: ull = (ULONGLONG)(*(PULONGLONG)p); break;
969 default: ASSERT(0); return FALSE; break;
970 }
971
972 ValueStack[ValueStackPointer++] = ull;
973 break;
974
975 case RpnOpDereference:
976 if (ValueStackPointer < 1)
977 {
978 CONST_STRCPY(ErrMsg, "Value stack underflow");
979
980 if (ErrOffset)
981 *ErrOffset = -1;
982
983 return FALSE;
984 }
985
986 /* FIXME: Print a warning when address is out of range */
987 p = (PVOID)(ULONG_PTR)ValueStack[ValueStackPointer - 1];
988 Ok = FALSE;
989
990 switch (Op->Data.DerefMemorySize)
991 {
992 case 1:
993 if (NT_SUCCESS(KdbpSafeReadMemory(&uc, p, sizeof (uc))))
994 {
995 Ok = TRUE;
996 ull = (ULONGLONG)uc;
997 }
998 break;
999
1000 case 2:
1001 if (NT_SUCCESS(KdbpSafeReadMemory(&us, p, sizeof (us))))
1002 {
1003 Ok = TRUE;
1004 ull = (ULONGLONG)us;
1005 }
1006 break;
1007
1008 case 4:
1009 if (NT_SUCCESS(KdbpSafeReadMemory(&ul, p, sizeof (ul))))
1010 {
1011 Ok = TRUE;
1012 ull = (ULONGLONG)ul;
1013 }
1014 break;
1015
1016 case 8:
1017 if (NT_SUCCESS(KdbpSafeReadMemory(&ull, p, sizeof (ull))))
1018 {
1019 Ok = TRUE;
1020 }
1021 break;
1022
1023 default:
1024 ASSERT(0);
1025 return FALSE;
1026 break;
1027 }
1028
1029 if (!Ok)
1030 {
1031 _snprintf(ErrMsg, 128, "Couldn't access memory at 0x%p", p);
1032
1033 if (ErrOffset)
1034 *ErrOffset = Op->CharacterOffset;
1035
1036 return FALSE;
1037 }
1038
1039 ValueStack[ValueStackPointer - 1] = ull;
1040 break;
1041
1043 if (ValueStackPointer < 2)
1044 {
1045 CONST_STRCPY(ErrMsg, "Value stack underflow");
1046
1047 if (ErrOffset)
1048 *ErrOffset = -1;
1049
1050 return FALSE;
1051 }
1052
1053 ValueStackPointer--;
1054 ull = ValueStack[ValueStackPointer];
1055
1056 if (ull == 0 && Op->Data.BinaryOperator == RpnBinaryOperatorDiv)
1057 {
1058 CONST_STRCPY(ErrMsg, "Division by zero");
1059
1060 if (ErrOffset)
1061 *ErrOffset = Op->CharacterOffset;
1062
1063 return FALSE;
1064 }
1065
1066 ull = Op->Data.BinaryOperator(ValueStack[ValueStackPointer - 1], ull);
1067 ValueStack[ValueStackPointer - 1] = ull;
1068 break;
1069
1070 default:
1071 ASSERT(0);
1072 return FALSE;
1073 }
1074 }
1075
1076#ifdef DEBUG_RPN
1077 DPRINT1("Max value stack pointer: %d\n", ValueStackPointerMax);
1078#endif
1079
1080 if (ValueStackPointer != 1)
1081 {
1082 CONST_STRCPY(ErrMsg, "Stack not empty after evaluation");
1083
1084 if (ErrOffset)
1085 *ErrOffset = -1;
1086
1087 return FALSE;
1088 }
1089
1090 *Result = ValueStack[0];
1091 return TRUE;
1092}
unsigned char BOOLEAN
#define index(s, c)
Definition: various.h:29
#define DPRINT1
Definition: precomp.h:8
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
@ Ok
Definition: gdiplustypes.h:26
GLuint index
Definition: glext.h:6031
GLfloat GLfloat p
Definition: glext.h:8902
NTSTATUS KdbpSafeReadMemory(OUT PVOID Dest, IN PVOID Src, IN ULONG Bytes)
Definition: kdb.c:1643
ULONGLONG RpnBinaryOperatorDiv(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:184
static const struct @1797 RegisterToTrapFrame[]
#define RPN_VALUE_STACK_SIZE
Definition: kdb_expr.c:93
static const BYTE us[]
Definition: encode.c:689
__GNU_EXTENSION typedef unsigned __int64 * PULONGLONG
Definition: ntbasedef.h:383
unsigned short USHORT
Definition: pedump.c:61
RPN_OP_TYPE Type
Definition: kdb_expr.c:57
RPN_BINARY_OPERATOR BinaryOperator
Definition: kdb_expr.c:62
ULONG CharacterOffset
Definition: kdb_expr.c:58
union _RPN_OP::@1798 Data
UCHAR DerefMemorySize
Definition: kdb_expr.c:68
ULONGLONG Immediate
Definition: kdb_expr.c:64
UCHAR Register
Definition: kdb_expr.c:66
#define max(a, b)
Definition: svc.c:63
uint32_t * PULONG
Definition: typedefs.h:59
void * PVOID
Definition: typedefs.h:50
uint16_t * PUSHORT
Definition: typedefs.h:56
uint32_t ULONG_PTR
Definition: typedefs.h:65
unsigned char * PUCHAR
Definition: typedefs.h:53
uint32_t ULONG
Definition: typedefs.h:59
uint64_t ULONGLONG
Definition: typedefs.h:67
unsigned char UCHAR
Definition: xmlstorage.h:181
#define _snprintf
Definition: xmlstorage.h:200

Referenced by KdbpRpnEvaluateExpression(), and KdbpRpnEvaluateParsedExpression().

◆ RpnpParseExpression()

static BOOLEAN RpnpParseExpression ( IN PRPN_STACK  Stack,
IN PCHAR  Expression,
OUT PCHAR *End  OPTIONAL,
IN ULONG  CharacterOffset,
OUT PLONG ErrOffset  OPTIONAL,
OUT PCHAR ErrMsg  OPTIONAL 
)
static

Parses an expression.

This functions parses the given expression until the end of string or a closing brace is found. As the function parses the string it pushes RPN_OPs onto the stack.

Examples: 1+2*3 ; eax+10 ; (eax+16) * (ebx+4) ; dword[eax]

Parameters
StackPointer to a RPN_STACK structure.
ExpressionString to parse.
CharacterOffsetCharacter offset of the subexpression from the beginning of the expression.
EndOn success End is set to the character at which parsing stopped.
ErrOffsetOn failure this is set to the character offset at which the error occoured.
ErrMsgOn failure a message describing the problem is copied into this buffer (128 bytes)
Return values
TRUESuccess.
FALSEFailure.

Definition at line 426 of file kdb_expr.c.

433{
435 PCHAR pend;
437 LONG OperatorOffset = -1;
438 RPN_OP RpnOp;
439 RPN_OP PoppedOperator;
440 BOOLEAN HavePoppedOperator = FALSE;
441 RPN_OP ComparativeOp;
442 BOOLEAN ComparativeOpFilled = FALSE;
443 BOOLEAN IsComparativeOp;
444 INT_PTR i, i2;
445 ULONG64 ull;
447 CHAR Buffer[16];
449
450 ASSERT(Stack);
452
453 First = TRUE;
454 for (;;)
455 {
456 /* Skip whitespace */
457 while (isspace(*p))
458 {
459 p++;
460 CharacterOffset++;
461 }
462
463 /* Check for end of expression */
464 if (p[0] == '\0' || p[0] == ')' || p[0] == ']')
465 break;
466
467 if (!First)
468 {
469 /* Remember operator */
470 Operator = p++;
471 OperatorOffset = CharacterOffset++;
472
473 /* Pop operator (to get the right operator precedence) */
474 HavePoppedOperator = FALSE;
475 if (*Operator == '*' || *Operator == '/' || *Operator == '%')
476 {
477 if (RpnpTopStack(Stack, &PoppedOperator) &&
478 PoppedOperator.Type == RpnOpBinaryOperator &&
479 (PoppedOperator.Data.BinaryOperator == RpnBinaryOperatorAdd ||
480 PoppedOperator.Data.BinaryOperator == RpnBinaryOperatorSub))
481 {
483 HavePoppedOperator = TRUE;
484 }
485 else if (PoppedOperator.Type == RpnOpNop)
486 {
488 /* Discard the NOP - it was only pushed to indicate there was a
489 * closing brace, so the previous operator shouldn't be popped.
490 */
491 }
492 }
493 else if ((Operator[0] == '=' && Operator[1] == '=') ||
494 (Operator[0] == '!' && Operator[1] == '=') ||
495 Operator[0] == '<' || Operator[0] == '>')
496 {
497 if (Operator[0] == '=' || Operator[0] == '!' ||
498 (Operator[0] == '<' && Operator[1] == '=') ||
499 (Operator[0] == '>' && Operator[1] == '='))
500 {
501 p++;
502 CharacterOffset++;
503 }
504#if 0
505 /* Parse rest of expression */
506 if (!RpnpParseExpression(Stack, p + 1, &pend, CharacterOffset + 1,
507 ErrOffset, ErrMsg))
508 {
509 return FALSE;
510 }
511 else if (pend == p + 1)
512 {
513 CONST_STRCPY(ErrMsg, "Expression expected");
514
515 if (ErrOffset)
516 *ErrOffset = CharacterOffset + 1;
517
518 return FALSE;
519 }
520
521 goto end_of_expression; /* return */
522#endif
523 }
524 else if (Operator[0] != '+' && Operator[0] != '-')
525 {
526 CONST_STRCPY(ErrMsg, "Operator expected");
527
528 if (ErrOffset)
529 *ErrOffset = OperatorOffset;
530
531 return FALSE;
532 }
533
534 /* Skip whitespace */
535 while (isspace(*p))
536 {
537 p++;
538 CharacterOffset++;
539 }
540 }
541
542 /* Get operand */
543 MemorySize = sizeof(ULONG_PTR); /* default to pointer size */
544
545get_operand:
546 i = strcspn(p, "+-*/%()[]<>!=");
547 if (i > 0)
548 {
549 i2 = i;
550
551 /* Copy register name/memory size */
552 while (isspace(p[--i2]));
553
554 i2 = min(i2 + 1, (INT)sizeof (Buffer) - 1);
555 strncpy(Buffer, p, i2);
556 Buffer[i2] = '\0';
557
558 /* Memory size prefix */
559 if (p[i] == '[')
560 {
561 if (stricmp(Buffer, "byte") == 0)
562 MemorySize = 1;
563 else if (stricmp(Buffer, "word") == 0)
564 MemorySize = 2;
565 else if (stricmp(Buffer, "dword") == 0)
566 MemorySize = 4;
567 else if (stricmp(Buffer, "qword") == 0)
568 MemorySize = 8;
569 else
570 {
571 CONST_STRCPY(ErrMsg, "Invalid memory size prefix");
572
573 if (ErrOffset)
574 *ErrOffset = CharacterOffset;
575
576 return FALSE;
577 }
578
579 p += i;
580 CharacterOffset += i;
581 goto get_operand;
582 }
583
584 /* Try to find register */
585 for (i = 0; i < RegisterToTrapFrameCount; i++)
586 {
588 break;
589 }
590
592 {
593 RpnOp.Type = RpnOpRegister;
594 RpnOp.CharacterOffset = CharacterOffset;
595 RpnOp.Data.Register = i;
597 CharacterOffset += i;
598 p += i;
599 }
600 else
601 {
602 /* Immediate value */
603 ull = strtoull(p, &pend, 0);
604 if (p != pend)
605 {
606 RpnOp.Type = RpnOpImmediate;
607 RpnOp.CharacterOffset = CharacterOffset;
608 RpnOp.Data.Immediate = ull;
609 CharacterOffset += pend - p;
610 p = pend;
611 }
612 else
613 {
614 CONST_STRCPY(ErrMsg, "Operand expected");
615
616 if (ErrOffset)
617 *ErrOffset = CharacterOffset;
618
619 return FALSE;
620 }
621 }
622
623 /* Push operand */
624 if (!RpnpPushStack(Stack, &RpnOp))
625 {
626 CONST_STRCPY(ErrMsg, "RPN op stack overflow");
627
628 if (ErrOffset)
629 *ErrOffset = -1;
630
631 return FALSE;
632 }
633 }
634 else if (i == 0)
635 {
636 if (p[0] == '(' || p[0] == '[') /* subexpression */
637 {
638 if (!RpnpParseExpression(Stack, p + 1, &pend, CharacterOffset + 1,
639 ErrOffset, ErrMsg))
640 {
641 return FALSE;
642 }
643 else if (pend == p + 1)
644 {
645 CONST_STRCPY(ErrMsg, "Expression expected");
646
647 if (ErrOffset)
648 *ErrOffset = CharacterOffset + 1;
649
650 return FALSE;
651 }
652
653 if (p[0] == '[') /* dereference */
654 {
655 ASSERT(MemorySize == 1 || MemorySize == 2 ||
656 MemorySize == 4 || MemorySize == 8);
657
658 if (pend[0] != ']')
659 {
660 CONST_STRCPY(ErrMsg, "']' expected");
661
662 if (ErrOffset)
663 *ErrOffset = CharacterOffset + (pend - p);
664
665 return FALSE;
666 }
667
668 RpnOp.Type = RpnOpDereference;
669 RpnOp.CharacterOffset = CharacterOffset;
671
672 if (!RpnpPushStack(Stack, &RpnOp))
673 {
674 CONST_STRCPY(ErrMsg, "RPN op stack overflow");
675
676 if (ErrOffset)
677 *ErrOffset = -1;
678
679 return FALSE;
680 }
681 }
682 else /* p[0] == '(' */
683 {
684 if (pend[0] != ')')
685 {
686 CONST_STRCPY(ErrMsg, "')' expected");
687
688 if (ErrOffset)
689 *ErrOffset = CharacterOffset + (pend - p);
690
691 return FALSE;
692 }
693 }
694
695 /* Push a "nop" to prevent popping of the + operator (which would
696 * result in (10+10)/2 beeing evaluated as 15)
697 */
698 RpnOp.Type = RpnOpNop;
699 if (!RpnpPushStack(Stack, &RpnOp))
700 {
701 CONST_STRCPY(ErrMsg, "RPN op stack overflow");
702
703 if (ErrOffset)
704 *ErrOffset = -1;
705
706 return FALSE;
707 }
708
709 /* Skip closing brace/bracket */
710 pend++;
711
712 CharacterOffset += pend - p;
713 p = pend;
714 }
715 else if (First && p[0] == '-') /* Allow expressions like "- eax" */
716 {
717 RpnOp.Type = RpnOpImmediate;
718 RpnOp.CharacterOffset = CharacterOffset;
719 RpnOp.Data.Immediate = 0;
720
721 if (!RpnpPushStack(Stack, &RpnOp))
722 {
723 CONST_STRCPY(ErrMsg, "RPN op stack overflow");
724
725 if (ErrOffset)
726 *ErrOffset = -1;
727
728 return FALSE;
729 }
730 }
731 else
732 {
733 CONST_STRCPY(ErrMsg, "Operand expected");
734
735 if (ErrOffset)
736 *ErrOffset = CharacterOffset;
737
738 return FALSE;
739 }
740 }
741 else
742 {
743 CONST_STRCPY(ErrMsg, "strcspn() failed");
744
745 if (ErrOffset)
746 *ErrOffset = -1;
747
748 return FALSE;
749 }
750
751 if (!First)
752 {
753 /* Push operator */
754 RpnOp.CharacterOffset = OperatorOffset;
756 IsComparativeOp = FALSE;
757
758 switch (*Operator)
759 {
760 case '+':
762 break;
763
764 case '-':
766 break;
767
768 case '*':
770 break;
771
772 case '/':
774 break;
775
776 case '%':
778 break;
779
780 case '=':
781 ASSERT(Operator[1] == '=');
782 IsComparativeOp = TRUE;
784 break;
785
786 case '!':
787 ASSERT(Operator[1] == '=');
788 IsComparativeOp = TRUE;
790 break;
791
792 case '<':
793 IsComparativeOp = TRUE;
794
795 if (Operator[1] == '=')
797 else
799
800 break;
801
802 case '>':
803 IsComparativeOp = TRUE;
804
805 if (Operator[1] == '=')
807 else
809
810 break;
811
812 default:
813 ASSERT(0);
814 break;
815 }
816
817 if (IsComparativeOp)
818 {
819 if (ComparativeOpFilled && !RpnpPushStack(Stack, &ComparativeOp))
820 {
821 CONST_STRCPY(ErrMsg, "RPN op stack overflow");
822
823 if (ErrOffset)
824 *ErrOffset = -1;
825
826 return FALSE;
827 }
828
829 memcpy(&ComparativeOp, &RpnOp, sizeof(RPN_OP));
830 ComparativeOpFilled = TRUE;
831 }
832 else if (!RpnpPushStack(Stack, &RpnOp))
833 {
834 CONST_STRCPY(ErrMsg, "RPN op stack overflow");
835
836 if (ErrOffset)
837 *ErrOffset = -1;
838
839 return FALSE;
840 }
841
842 /* Push popped operator */
843 if (HavePoppedOperator)
844 {
845 if (!RpnpPushStack(Stack, &PoppedOperator))
846 {
847 CONST_STRCPY(ErrMsg, "RPN op stack overflow");
848
849 if (ErrOffset)
850 *ErrOffset = -1;
851
852 return FALSE;
853 }
854 }
855 }
856
857 First = FALSE;
858 }
859
860//end_of_expression:
861
862 if (ComparativeOpFilled && !RpnpPushStack(Stack, &ComparativeOp))
863 {
864 CONST_STRCPY(ErrMsg, "RPN op stack overflow");
865
866 if (ErrOffset)
867 *ErrOffset = -1;
868
869 return FALSE;
870 }
871
872 /* Skip whitespace */
873 while (isspace(*p))
874 {
875 p++;
876 CharacterOffset++;
877 }
878
879 if (End)
880 *End = p;
881
882 return TRUE;
883}
WCHAR First[]
Definition: FormatMessage.c:11
#define isspace(c)
Definition: acclib.h:69
ACPI_SIZE strlen(const char *String)
Definition: utclib.c:269
char * strncpy(char *DstString, const char *SrcString, ACPI_SIZE Count)
Definition: utclib.c:427
@ Operator
Definition: asmpp.cpp:44
Definition: bufpool.h:45
#define ULONG_PTR
Definition: config.h:101
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
static BOOLEAN RpnpPushStack(IN OUT PRPN_STACK Stack, IN PRPN_OP Op)
Pushes an RPN_OP onto the stack.
Definition: kdb_expr.c:342
ULONGLONG RpnBinaryOperatorSub(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:168
ULONGLONG RpnBinaryOperatorGreaterThanOrEquals(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:240
static const INT RegisterToTrapFrameCount
Definition: kdb_expr.c:155
ULONGLONG RpnBinaryOperatorGreaterThan(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:232
#define stricmp
Definition: kdb_expr.c:83
ULONGLONG RpnBinaryOperatorMod(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:192
ULONGLONG RpnBinaryOperatorLessThanOrEquals(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:224
static BOOLEAN RpnpPopStack(IN OUT PRPN_STACK Stack, OUT PRPN_OP Op OPTIONAL)
Pops the top op from the stack.
Definition: kdb_expr.c:367
ULONGLONG RpnBinaryOperatorNotEquals(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:208
static BOOLEAN RpnpTopStack(IN PRPN_STACK Stack, OUT PRPN_OP Op)
Gets the top op from the stack (not popping it)
Definition: kdb_expr.c:392
ULONGLONG RpnBinaryOperatorAdd(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:160
ULONGLONG RpnBinaryOperatorMul(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:176
ULONGLONG RpnBinaryOperatorLessThan(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:216
ULONGLONG RpnBinaryOperatorEquals(ULONGLONG a, ULONGLONG b)
Definition: kdb_expr.c:200
unsigned __int64 ULONG64
Definition: imports.h:198
#define min(a, b)
Definition: monoChain.cc:55
_Check_return_ _CRTIMP size_t __cdecl strcspn(_In_z_ const char *_Str, _In_z_ const char *_Control)
#define strtoull
Definition: stabs.c:58
static CONST DWORD MemorySize[]
Definition: svga.c:32
int32_t INT_PTR
Definition: typedefs.h:64
int32_t INT
Definition: typedefs.h:58
char * PCHAR
Definition: typedefs.h:51
char CHAR
Definition: xmlstorage.h:175

Referenced by KdbpRpnEvaluateExpression(), KdbpRpnParseExpression(), and RpnpParseExpression().

◆ RpnpPopStack()

static BOOLEAN RpnpPopStack ( IN OUT PRPN_STACK  Stack,
OUT PRPN_OP Op  OPTIONAL 
)
static

Pops the top op from the stack.

Parameters
StackPointer to a RPN_STACK structure.
OpPointer to an RPN_OP to store the popped op into (can be NULL).
Return values
TRUESuccess.
FALSEFailure (stack empty)

Definition at line 367 of file kdb_expr.c.

370{
371 ASSERT(Stack);
372
373 if (Stack->Sp == 0)
374 return FALSE;
375
376 Stack->Sp--;
377 if (Op)
378 memcpy(Op, Stack->Ops + Stack->Sp, sizeof (RPN_OP));
379
380 return TRUE;
381}
ActualNumberDriverObjects * sizeof(PDRIVER_OBJECT)) PDRIVER_OBJECT *DriverObjectList

Referenced by RpnpParseExpression().

◆ RpnpPushStack()

static BOOLEAN RpnpPushStack ( IN OUT PRPN_STACK  Stack,
IN PRPN_OP  Op 
)
static

Pushes an RPN_OP onto the stack.

Parameters
StackPointer to a RPN_STACK structure.
OpRPN_OP to be copied onto the stack.

Definition at line 342 of file kdb_expr.c.

345{
346 ASSERT(Stack);
347 ASSERT(Op);
348
349 if (Stack->Sp >= Stack->Size)
350 return FALSE;
351
352 memcpy(Stack->Ops + Stack->Sp, Op, sizeof (RPN_OP));
353 Stack->Sp++;
354
355 return TRUE;
356}

Referenced by RpnpParseExpression().

◆ RpnpTopStack()

static BOOLEAN RpnpTopStack ( IN PRPN_STACK  Stack,
OUT PRPN_OP  Op 
)
static

Gets the top op from the stack (not popping it)

Parameters
StackPointer to a RPN_STACK structure.
OpPointer to an RPN_OP to copy the top op into.
Return values
TRUESuccess.
FALSEFailure (stack empty)

Definition at line 392 of file kdb_expr.c.

395{
396 ASSERT(Stack);
397 ASSERT(Op);
398
399 if (Stack->Sp == 0)
400 return FALSE;
401
402 memcpy(Op, Stack->Ops + Stack->Sp - 1, sizeof (RPN_OP));
403
404 return TRUE;
405}

Referenced by RpnpParseExpression().

Variable Documentation

◆ Name

Definition at line 110 of file kdb_expr.c.

◆ Offset

Definition at line 111 of file kdb_expr.c.

◆ Ops

Definition at line 100 of file kdb_expr.c.

Referenced by KdbpRpnParseExpression().

◆ 

const struct { ... } RegisterToTrapFrame[]

◆ RegisterToTrapFrameCount

const INT RegisterToTrapFrameCount = sizeof (RegisterToTrapFrame) / sizeof (RegisterToTrapFrame[0])
static

Definition at line 155 of file kdb_expr.c.

Referenced by RpnpParseExpression().

◆ 

struct { ... } RpnStack
Initial value:
=
{
0
}
#define RPN_OP_STACK_SIZE
Definition: kdb_expr.c:92

Referenced by KdbpRpnEvaluateExpression(), and KdbpRpnParseExpression().

◆ Size

Definition at line 98 of file kdb_expr.c.

Referenced by KdbpRpnParseExpression().

◆ Sp

ULONG Sp

Definition at line 99 of file kdb_expr.c.