- Use _SEH2_YIELD when returning from an exception instead of returning outside the...
[reactos.git] / reactos / lib / rtl / debug.c
index d053423..f34adef 100644 (file)
@@ -1,7 +1,7 @@
 /*
  * COPYRIGHT:       See COPYING in the top level directory
  * PROJECT:         ReactOS Run-Time Library
- * FILE:            ntoskrnl/rtl/dbgprint.c
+ * FILE:            lib/rtl/debug.c
  * PURPOSE:         Debug Print and Prompt routines
  * PROGRAMMERS:     Alex Ionescu (alex@relsoft.net)
  *                  Royce Mitchel III
@@ -16,7 +16,6 @@
 
 /* PRIVATE FUNCTIONS ********************************************************/
 
-#if 0
 NTSTATUS
 NTAPI
 DebugPrint(IN PANSI_STRING DebugString,
@@ -28,20 +27,13 @@ DebugPrint(IN PANSI_STRING DebugString,
                         DebugString->Buffer,
                         DebugString->Length,
                         UlongToPtr(ComponentId),
-                        UlongToPtr(Level)); 
+                        UlongToPtr(Level));
 }
-#else
-NTSTATUS
-NTAPI
-DebugPrint(IN PANSI_STRING DebugString,
-           IN ULONG ComponentId,
-           IN ULONG Level);
-#endif
 
 NTSTATUS
 NTAPI
-DebugPrompt(IN PANSI_STRING Output,
-            IN PANSI_STRING Input)
+DebugPrompt(IN PCSTRING Output,
+            IN PSTRING Input)
 {
     /* Call the INT2D Service */
     return DebugService(BREAKPOINT_PROMPT,
@@ -65,13 +57,12 @@ vDbgPrintExWithPrefixInternal(IN LPCSTR Prefix,
     NTSTATUS Status;
     ANSI_STRING DebugString;
     CHAR Buffer[512];
-    PCHAR pBuffer = Buffer;
-    ULONG pBufferSize = sizeof(Buffer);
-    ULONG Length;
+    ULONG Length, PrefixLength;
     EXCEPTION_RECORD ExceptionRecord;
 
     /* Check if we should print it or not */
-    if (ComponentId != -1 && !NtQueryDebugFilterState(ComponentId, Level))
+    if ((ComponentId != -1U) &&
+        !(NtQueryDebugFilterState(ComponentId, Level)))
     {
         /* This message is masked */
         return STATUS_SUCCESS;
@@ -80,36 +71,32 @@ vDbgPrintExWithPrefixInternal(IN LPCSTR Prefix,
     /* For user mode, don't recursively DbgPrint */
     if (RtlpSetInDbgPrint(TRUE)) return STATUS_SUCCESS;
 
-    /* Initialize the length to 8 */
-    DebugString.Length = 0;
-
-    /* Handle the prefix */
-    if (Prefix && *Prefix)
+    /* Guard against incorrect pointers */
+    _SEH2_TRY
     {
-        /* Get the length */
-        DebugString.Length = strlen(Prefix);
-
-        /* Normalize it */
-        if(DebugString.Length > sizeof(Buffer))
-        {
-            DebugString.Length = sizeof(Buffer);
-        }
+        /* Get the length and normalize it */
+        PrefixLength = strlen(Prefix);
+        if (PrefixLength > sizeof(Buffer)) PrefixLength = sizeof(Buffer);
 
         /* Copy it */
-        strncpy(Buffer, Prefix, DebugString.Length);
+        strncpy(Buffer, Prefix, PrefixLength);
 
-        /* Set the pointer and update the size */
-        pBuffer = &Buffer[DebugString.Length];
-        pBufferSize -= DebugString.Length;
+        /* Do the printf */
+        Length = _vsnprintf(Buffer + PrefixLength,
+                            sizeof(Buffer) - PrefixLength,
+                            Format,
+                            ap);
     }
-
-    /* Setup the ANSI String */
-    DebugString.Buffer = Buffer;
-    DebugString.MaximumLength = sizeof(Buffer);
-    Length = _vsnprintf(pBuffer, pBufferSize, Format, ap);
+    _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
+    {
+        /* Fail */
+        Length = PrefixLength = 0;
+        _SEH2_YIELD(return _SEH2_GetExceptionCode());
+    }
+    _SEH2_END;
 
     /* Check if we went past the buffer */
-    if (Length == -1)
+    if (Length == -1U)
     {
         /* Terminate it if we went over-board */
         Buffer[sizeof(Buffer) - 1] = '\n';
@@ -117,9 +104,15 @@ vDbgPrintExWithPrefixInternal(IN LPCSTR Prefix,
         /* Put maximum */
         Length = sizeof(Buffer);
     }
+    else
+    {
+        /* Add the prefix */
+        Length += PrefixLength;
+    }
 
-    /* Update length */
-    DebugString.Length += Length;
+    /* Build the string */
+    DebugString.Length = Length;
+    DebugString.Buffer = Buffer;
 
     /* First, let the debugger know as well */
     if (RtlpCheckForActiveDebugger(FALSE))
@@ -150,7 +143,7 @@ vDbgPrintExWithPrefixInternal(IN LPCSTR Prefix,
         if (Status == STATUS_BREAKPOINT)
         {
             /* Breakpoint */
-            DbgBreakPointWithStatus(DBG_STATUS_CONTROL_C);
+            //DbgBreakPointWithStatus(DBG_STATUS_CONTROL_C);
             Status = STATUS_SUCCESS;
         }
     }
@@ -193,7 +186,7 @@ vDbgPrintEx(IN ULONG ComponentId,
             IN va_list ap)
 {
     /* Call the internal routine that also handles ControlC */
-    return vDbgPrintExWithPrefixInternal(NULL,
+    return vDbgPrintExWithPrefixInternal("",
                                          ComponentId,
                                          Level,
                                          Format,
@@ -209,17 +202,19 @@ __cdecl
 DbgPrint(PCCH Format,
          ...)
 {
+    ULONG n;
     va_list ap;
 
     /* Call the internal routine that also handles ControlC */
     va_start(ap, Format);
-    return vDbgPrintExWithPrefixInternal(NULL,
-                                         -1,
-                                         DPFLTR_ERROR_LEVEL,
-                                         Format,
-                                         ap,
-                                         TRUE);
+    n = vDbgPrintExWithPrefixInternal("",
+                                      -1,
+                                      DPFLTR_ERROR_LEVEL,
+                                      Format,
+                                      ap,
+                                      TRUE);
     va_end(ap);
+    return n;
 }
 
 /*
@@ -232,17 +227,19 @@ DbgPrintEx(IN ULONG ComponentId,
            IN PCCH Format,
            ...)
 {
+    ULONG n;
     va_list ap;
 
     /* Call the internal routine that also handles ControlC */
     va_start(ap, Format);
-    return vDbgPrintExWithPrefixInternal(NULL,
-                                         ComponentId,
-                                         Level,
-                                         Format,
-                                         ap,
-                                         TRUE);
+    n = vDbgPrintExWithPrefixInternal("",
+                                      ComponentId,
+                                      Level,
+                                      Format,
+                                      ap,
+                                      TRUE);
     va_end(ap);
+    return n;
 }
 
 /*
@@ -253,16 +250,19 @@ __cdecl
 DbgPrintReturnControlC(PCH Format,
                        ...)
 {
+    ULONG n;
     va_list ap;
 
     /* Call the internal routine that also handles ControlC */
     va_start(ap, Format);
-    return vDbgPrintExWithPrefixInternal(NULL,
-                                         -1,
-                                         DPFLTR_ERROR_LEVEL,
-                                         Format,
-                                         ap,
-                                         FALSE);
+    n = vDbgPrintExWithPrefixInternal("",
+                                      -1,
+                                      DPFLTR_ERROR_LEVEL,
+                                      Format,
+                                      ap,
+                                      FALSE);
+    va_end(ap);
+    return n;
 }
 
 /*
@@ -270,20 +270,20 @@ DbgPrintReturnControlC(PCH Format,
  */
 ULONG
 NTAPI
-DbgPrompt(PCCH OutputString,
-          PCH InputString,
-          ULONG InputSize)
+DbgPrompt(IN PCCH Prompt,
+          OUT PCH Response,
+          IN ULONG MaximumResponseLength)
 {
-    ANSI_STRING Output;
-    ANSI_STRING Input;
+    CSTRING Output;
+    STRING Input;
 
     /* Setup the input string */
-    Input.MaximumLength = InputSize;
-    Input.Buffer = InputString;
+    Input.MaximumLength = (USHORT)MaximumResponseLength;
+    Input.Buffer = Response;
 
     /* Setup the output string */
-    Output.Length = strlen (OutputString);
-    Output.Buffer = OutputString;
+    Output.Length = strlen(Prompt);
+    Output.Buffer = Prompt;
 
     /* Call the system service */
     return DebugPrompt(&Output, &Input);
@@ -292,7 +292,7 @@ DbgPrompt(PCCH OutputString,
 /*
  * @implemented
  */
-BOOLEAN
+NTSTATUS
 NTAPI
 DbgQueryDebugFilterState(IN ULONG ComponentId,
                          IN ULONG Level)
@@ -315,15 +315,56 @@ DbgSetDebugFilterState(IN ULONG ComponentId,
 }
 
 /*
- * @unimplemented
+ * @implemented
  */
 NTSTATUS
 NTAPI
-DbgLoadImageSymbols(IN PUNICODE_STRING Name,
-                    IN ULONG Base,
-                    IN ULONG Unknown3)
+DbgLoadImageSymbols(IN PANSI_STRING Name,
+                    IN PVOID Base,
+                    IN ULONG_PTR ProcessId)
+{
+    PIMAGE_NT_HEADERS NtHeader;
+    KD_SYMBOLS_INFO SymbolInfo;
+
+    /* Setup the symbol data */
+    SymbolInfo.BaseOfDll = Base;
+    SymbolInfo.ProcessId = (ULONG)ProcessId;
+
+    /* Get NT Headers */
+    NtHeader = RtlImageNtHeader(Base);
+    if (NtHeader)
+    {
+        /* Get the rest of the data */
+        SymbolInfo.CheckSum = NtHeader->OptionalHeader.CheckSum;
+        SymbolInfo.SizeOfImage = NtHeader->OptionalHeader.SizeOfImage;
+    }
+    else
+    {
+        /* No data available */
+        SymbolInfo.CheckSum = SymbolInfo.SizeOfImage = 0;
+    }
+
+    /* Load the symbols */
+    DebugService2(Name, &SymbolInfo, BREAKPOINT_LOAD_SYMBOLS);
+    return STATUS_SUCCESS;
+}
+
+/*
+ * @implemented
+ */
+VOID
+NTAPI
+DbgUnLoadImageSymbols(IN PANSI_STRING Name,
+                      IN PVOID Base,
+                      IN ULONG_PTR ProcessId)
 {
-    UNIMPLEMENTED;
-    return STATUS_NOT_IMPLEMENTED;
+    KD_SYMBOLS_INFO SymbolInfo;
+
+    /* Setup the symbol data */
+    SymbolInfo.BaseOfDll = Base;
+    SymbolInfo.ProcessId = (ULONG)ProcessId;
+    SymbolInfo.CheckSum = SymbolInfo.SizeOfImage = 0;
+
+    /* Load the symbols */
+    DebugService2(Name, &SymbolInfo, BREAKPOINT_UNLOAD_SYMBOLS);
 }
-/* EOF */