Added API for compiler host to choose a different output path on output error
git-svn-id: https://svn.code.sf.net/p/nsis/code/NSIS/trunk@7169 212acab6-be3b-0410-9dea-997c60f758d6
This commit is contained in:
parent
13121dacfe
commit
322c7ac6d2
6 changed files with 131 additions and 15 deletions
|
@ -2646,8 +2646,8 @@ int CEXEBuild::write_output(void)
|
|||
|
||||
RET_UNLESS_OK( uninstall_generate() );
|
||||
|
||||
crc32_t crc=0;
|
||||
|
||||
unsigned char limit = 0; // Limit the number of retries in case the host has some kind of bug
|
||||
retry_output:
|
||||
{
|
||||
tstring full_path = get_full_path(build_output_filename), fnamebuf = get_file_name(build_output_filename);
|
||||
notify(MakensisAPI::NOTIFY_OUTPUT, full_path.c_str());
|
||||
|
@ -2667,6 +2667,7 @@ int CEXEBuild::write_output(void)
|
|||
if (!fp)
|
||||
{
|
||||
ERROR_MSG(_T("Can't open output file\n"));
|
||||
if (++limit && prompt_for_output_path(build_output_filename, COUNTOF(CEXEBuild::build_output_filename))) goto retry_output;
|
||||
return PS_ERROR;
|
||||
}
|
||||
|
||||
|
@ -2677,6 +2678,7 @@ int CEXEBuild::write_output(void)
|
|||
return PS_ERROR;
|
||||
}
|
||||
|
||||
crc32_t crc=0;
|
||||
#ifdef NSIS_CONFIG_CRC_SUPPORT
|
||||
#ifdef NSIS_CONFIG_CRC_ANAL
|
||||
crc=CRC32(crc,m_exehead,(DWORD)m_exehead_size);
|
||||
|
@ -3479,7 +3481,7 @@ void CEXEBuild::warninghelper(DIAGCODE dc, bool fl, const TCHAR *fmt, va_list ar
|
|||
|
||||
m_warnings.add(msg,0); // Add to list of warnings to display at the end
|
||||
|
||||
MakensisAPI::notify_e hostevent = MakensisAPI::NOTIFY_WARNING;
|
||||
MakensisAPI::datatransfer_e hostevent = MakensisAPI::NOTIFY_WARNING;
|
||||
if (aserror)
|
||||
hostevent = MakensisAPI::NOTIFY_ERROR, display_warnings = display_errors;
|
||||
|
||||
|
@ -3571,7 +3573,7 @@ void CEXEBuild::print_warnings()
|
|||
FlushOutputAndResetPrintColor();
|
||||
}
|
||||
|
||||
void CEXEBuild::notify(MakensisAPI::notify_e code, const TCHAR *data) const
|
||||
void CEXEBuild::notify(MakensisAPI::datatransfer_e code, const TCHAR *data) const
|
||||
{
|
||||
#ifdef _WIN32
|
||||
if (notify_hwnd)
|
||||
|
@ -3595,6 +3597,64 @@ void CEXEBuild::notify(MakensisAPI::notify_e code, const TCHAR *data) const
|
|||
#endif
|
||||
}
|
||||
|
||||
bool CEXEBuild::hostapi_request_data(MakensisAPI::datatransfer_e operation, UINT minver, HOSTAPIREQUESTDATAPROC proc, void*cookie, const void* input, UINT inputsize) const
|
||||
{
|
||||
using namespace MakensisAPI;
|
||||
#ifdef _WIN32
|
||||
struct helper {
|
||||
static INT_PTR CALLBACK Proc(HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
size_t *data = (size_t*) GetWindowLongPtr(hWnd, DWLP_USER);
|
||||
if (Msg == WM_CLOSE)
|
||||
{
|
||||
if (lParam) SendMessage((HWND) wParam, WM_COPYDATA, (SIZE_T) hWnd, lParam);
|
||||
return DestroyWindow(hWnd) | PostMessage(NULL, WM_QUIT, 0, 0);
|
||||
}
|
||||
return data && ((HOSTAPIREQUESTDATAPROC)data[0])((void*) data[1], hWnd, Msg, wParam, lParam); // We don't set DWLP_MSGRESULT nor care about the return value
|
||||
}
|
||||
};
|
||||
if (!notify_hwnd || (minver && SendMessage(notify_hwnd, QUERYHOST, QH_SUPPORTEDVERSION, 0) < minver)) return false;
|
||||
size_t data[] = { (size_t) proc, (size_t) cookie };
|
||||
COPYDATASTRUCT cds = { (DWORD) operation, inputsize, (void*) input };
|
||||
HWND hWnd = CreateWindowEx(WS_EX_TOOLWINDOW, WC_DIALOG, NULL, WS_POPUP|WS_DISABLED, 0, 0, 0, 0, NULL, NULL, NULL, NULL);
|
||||
SetWindowLongPtr(hWnd, DWLP_USER, (LONG_PTR) data);
|
||||
SetWindowLongPtr(hWnd, DWLP_DLGPROC, (LONG_PTR) helper::Proc);
|
||||
SendMessage(hWnd, WM_CLOSE, (SIZE_T) notify_hwnd, (SIZE_T) &cds);
|
||||
for (MSG msg; (int) GetMessage(&msg, NULL, 0, 0) > 0;) DispatchMessage(&msg);
|
||||
return true;
|
||||
#else
|
||||
return false;
|
||||
#endif
|
||||
}
|
||||
|
||||
bool CEXEBuild::prompt_for_output_path(TCHAR*path, UINT pathcap) const
|
||||
{
|
||||
using namespace MakensisAPI;
|
||||
#ifdef _WIN32
|
||||
struct handler {
|
||||
static bool CALLBACK proc(void*cookie, HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
size_t *io = (size_t*) cookie;
|
||||
COPYDATASTRUCT*pCDS = (COPYDATASTRUCT*) lParam;
|
||||
if (Msg == WM_COPYDATA && pCDS->cbData > sizeof(TCHAR) && pCDS->cbData <= io[2] * sizeof(TCHAR))
|
||||
{
|
||||
_tcscpy((TCHAR*) io[1], (TCHAR*) ((COPYDATASTRUCT*)lParam)->lpData);
|
||||
return (io[0] = pCDS->dwData == PROMPT_FILEPATH);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
};
|
||||
size_t io[] = { false, (size_t) path, pathcap }, cb;
|
||||
TinyGrowBuf inputbuf((cb = FIELD_OFFSET(PROMPT_FILEPATH_DATA, Path[pathcap])));
|
||||
PROMPT_FILEPATH_DATA *p = (PROMPT_FILEPATH_DATA*) inputbuf.get();
|
||||
p->Platform = (sizeof(void*) * 8) | sizeof(TCHAR), p->Reserved = 0;
|
||||
_tcscpy(p->Path, path);
|
||||
return hostapi_request_data(PROMPT_FILEPATH, 0x03006000, handler::proc, io, p, cb) && io[0];
|
||||
#else
|
||||
return false;
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifdef NSIS_CONFIG_PLUGIN_SUPPORT
|
||||
int CEXEBuild::initialize_default_plugins(bool newtargetarc)
|
||||
{
|
||||
|
|
|
@ -143,11 +143,12 @@ namespace MakensisAPI {
|
|||
extern const TCHAR* SigintEventNameFmt;
|
||||
extern const TCHAR* SigintEventNameLegacy;
|
||||
|
||||
enum notify_e {
|
||||
NOTIFY_SCRIPT, // main nsi file(s)
|
||||
enum datatransfer_e {
|
||||
NOTIFY_SCRIPT, // Compiler -> Host: main nsi file(s)
|
||||
NOTIFY_WARNING,
|
||||
NOTIFY_ERROR,
|
||||
NOTIFY_OUTPUT // generated .exe file
|
||||
NOTIFY_OUTPUT, // Compiler -> Host: Generated .exe file
|
||||
PROMPT_FILEPATH // [0x03006000] Compiler -> Host -> Compiler
|
||||
};
|
||||
#ifdef _WIN32
|
||||
enum sndmsg_e {
|
||||
|
@ -156,8 +157,14 @@ namespace MakensisAPI {
|
|||
#endif
|
||||
enum QUERYHOST_e {
|
||||
QH_OUTPUTCHARSET = 1, // [0x03000000] return (wincodepage+1) or 0 for default (This encoding is used by stdout, stderr and the notify messages)
|
||||
QH_ENABLESTDERR // [0x03001000] return 1 to output error messages to stderr or 0 to output error messages to stdout
|
||||
QH_ENABLESTDERR, // [0x03001000] return 1 to output error messages to stderr or 0 to output error messages to stdout
|
||||
QH_SUPPORTEDVERSION, // [0x03006000] The host must return new highest makensis compiler version it supports
|
||||
};
|
||||
typedef struct {
|
||||
unsigned char Platform; // Bitness OR'ed with sizeof(TCHAR) of the compiler
|
||||
unsigned char Reserved;
|
||||
TCHAR Path[1];
|
||||
} PROMPT_FILEPATH_DATA;
|
||||
}
|
||||
|
||||
#define PAGE_CUSTOM 0
|
||||
|
@ -273,7 +280,14 @@ class CEXEBuild {
|
|||
NStreamLineReader* curlinereader;
|
||||
|
||||
HWND notify_hwnd;
|
||||
void notify(MakensisAPI::notify_e code, const TCHAR *data) const;
|
||||
void notify(MakensisAPI::datatransfer_e code, const TCHAR *data) const;
|
||||
#ifdef _WIN32
|
||||
typedef bool (CALLBACK*HOSTAPIREQUESTDATAPROC)(void*cookie, HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam);
|
||||
#else
|
||||
typedef bool (*HOSTAPIREQUESTDATAPROC)(void*cookie);
|
||||
#endif
|
||||
bool hostapi_request_data(MakensisAPI::datatransfer_e operation, UINT minver, HOSTAPIREQUESTDATAPROC proc, void*cookie, const void* input, UINT inputsize) const;
|
||||
bool prompt_for_output_path(TCHAR*path, UINT pathcap) const;
|
||||
|
||||
private:
|
||||
int check_write_output_errors() const;
|
||||
|
|
|
@ -122,6 +122,7 @@ class GrowBuf : public IGrowBuf
|
|||
class TinyGrowBuf : public GrowBuf {
|
||||
public:
|
||||
TinyGrowBuf() : GrowBuf() { m_bs=1024; }
|
||||
TinyGrowBuf(size_type cb) : GrowBuf() { m_bs=1024; resize(cb); }
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue