* CopyErrorData --- obtain a copy of the topmost error stack entry * * This is only for use in error handler code. The data is copied into the * current memory context, so callers should always switch away from * ErrorContext first; otherwise it will be lost when FlushErrorState is done. */
| 1821 | * ErrorContext first; otherwise it will be lost when FlushErrorState is done. |
| 1822 | */ |
| 1823 | ErrorData * |
| 1824 | CopyErrorData(void) |
| 1825 | { |
| 1826 | ErrorData *edata = &errordata[errordata_stack_depth]; |
| 1827 | ErrorData *newedata; |
| 1828 | |
| 1829 | /* |
| 1830 | * we don't increment recursion_depth because out-of-memory here does not |
| 1831 | * indicate a problem within the error subsystem. |
| 1832 | */ |
| 1833 | CHECK_STACK_DEPTH(); |
| 1834 | |
| 1835 | Assert(CurrentMemoryContext != ErrorContext); |
| 1836 | |
| 1837 | /* Copy the struct itself */ |
| 1838 | newedata = (ErrorData *) palloc(sizeof(ErrorData)); |
| 1839 | memcpy(newedata, edata, sizeof(ErrorData)); |
| 1840 | |
| 1841 | /* Make copies of separately-allocated fields */ |
| 1842 | if (newedata->message) |
| 1843 | newedata->message = pstrdup(newedata->message); |
| 1844 | if (newedata->detail) |
| 1845 | newedata->detail = pstrdup(newedata->detail); |
| 1846 | if (newedata->detail_log) |
| 1847 | newedata->detail_log = pstrdup(newedata->detail_log); |
| 1848 | if (newedata->hint) |
| 1849 | newedata->hint = pstrdup(newedata->hint); |
| 1850 | if (newedata->context) |
| 1851 | newedata->context = pstrdup(newedata->context); |
| 1852 | if (newedata->backtrace) |
| 1853 | newedata->backtrace = pstrdup(newedata->backtrace); |
| 1854 | if (newedata->schema_name) |
| 1855 | newedata->schema_name = pstrdup(newedata->schema_name); |
| 1856 | if (newedata->table_name) |
| 1857 | newedata->table_name = pstrdup(newedata->table_name); |
| 1858 | if (newedata->column_name) |
| 1859 | newedata->column_name = pstrdup(newedata->column_name); |
| 1860 | if (newedata->datatype_name) |
| 1861 | newedata->datatype_name = pstrdup(newedata->datatype_name); |
| 1862 | if (newedata->constraint_name) |
| 1863 | newedata->constraint_name = pstrdup(newedata->constraint_name); |
| 1864 | if (newedata->internalquery) |
| 1865 | newedata->internalquery = pstrdup(newedata->internalquery); |
| 1866 | |
| 1867 | /* Use the calling context for string allocation */ |
| 1868 | newedata->assoc_context = CurrentMemoryContext; |
| 1869 | |
| 1870 | return newedata; |
| 1871 | } |
| 1872 | |
| 1873 | /* |
| 1874 | * FreeErrorData --- free the structure returned by CopyErrorData. |