NSISPlugins.rst (4049B)
1 ===================== 2 Building NSIS Plugins 3 ===================== 4 5 .. note:: 6 7 This guide assumes that you have a Firefox build environment set up as well as a recent version of Visual Studio. The steps here use Visual Studio 2022. 8 9 Instructions 10 ------------ 11 12 1. Make sure you are configured to build DLLs. Follow this `guide <https://learn.microsoft.com/en-us/cpp/build/walkthrough-creating-and-using-a-dynamic-link-library-cpp>`_. 13 2. NSIS plugins are not integrated with the build system pending `bug 1771192 <https://bugzilla.mozilla.org/show_bug.cgi?id=1771192>`_. You will need to build them manually by creating a new Visual Studio project in the ``$SRCDIR/other-licenses/nsis/Contrib/`` directory with the following settings. 14 15 .. image:: newProjectDllVS.png 16 .. image:: projectSettingsDllVS.png 17 18 3. Once the project has been created, right click on it in the sidebar and go to ``Configuration Properties -> C/C++ -> Precompiled Header`` and set ``Precompiled Header`` to "Not Using Precompiled Headers". 19 20 .. image:: projectPropertyPageVS.png 21 22 4. For easier testing set the output directory in ``Configuration Properties -> General`` to ``$SRCDIR/other-licenses/nsis/Plugins``. 23 24 5. Delete any files generated when you created the Visual Studio project such as ``pch.h`` or ``framework.h`` and any related include statements. 25 26 6. Download the source code for `NSIS version 3.07 <https://sourceforge.net/projects/nsis/files/NSIS%203/3.07/>`_. (current at the time of writing although possibly subject to change) and extract the source files. Navigate to ``Contrib/ExDLL`` and copy ``pluginapi.h``, ``pluginapi.c`` and ``nsis_tchar.h`` to where header files for your Visual Studio project live. Add them to your project. 27 28 7. You can use the following template to get started with your own plugin: 29 30 .. code:: cpp 31 32 /* This Source Code Form is subject to the terms of the Mozilla Public 33 * License, v. 2.0. If a copy of the MPL was not distributed with this 34 * file, you can obtain one at http://mozilla.org/MPL/2.0/. */ 35 36 // Put a brief description of your NSIS plugin here. 37 38 // Put your include statements here. 39 #include <sysheader> 40 #include "pluginapi.h" // This is taken from the NSIS plugin page 41 #include "myheader.h" 42 43 // A struct used for reading the stack passed in to the function 44 struct stack_t { 45 stack_t* next; 46 TCHAR text[MAX_PATH]; 47 }; 48 49 /** 50 * 51 * 52 * Put any additional functions you write here. 53 * 54 * 55 */ 56 57 // I use popstringn and pushstringn from the NSIS pluginapi.h file. 58 59 // This is the function I want to call from within NSIS 60 extern "C" void __declspec(dllexport) 61 MyNSISFunction(HWND, int string_size, TCHAR* variables, stack_t** stacktop, void*) { 62 wchar_t getArg[MAX_PATH+1]; 63 EXDLL_INIT(); 64 bool rv = false; 65 int popRet = popstringn(getArg, MAX_PATH+1); 66 if (popRet == 0) { 67 rv = FunctionThatTakesAnArgument(getArg); 68 } 69 pushstring(rv ? L"1" : L"0"); 70 } 71 72 BOOL APIENTRY 73 DllMain(HMODULE, DWORD, LPVOID) { 74 return TRUE; 75 } 76 77 8. Modify ``$SRCDIR/toolkit/mozapps/installer/windows/nsis/makensis.mk`` as follows: 78 79 .. code:: text 80 81 CUSTOM_NSIS_PLUGINS = \ 82 ... \ 83 MyPlugin.dll \ 84 ... \ 85 $(NULL) 86 87 88 9. **NSIS only works with 32-bit plugins so ensure your Visual Studio build configuration is set to x86.** Compile your new plugin. ``exp`` and ``lib`` files will also be generated but they can safely be deleted. 89 90 10. The plugin can now be called from within NSIS as follows: 91 92 .. code:: text 93 94 MyPlugin::MyNSISFunc "$myNSISarg" 95 96 .. note:: 97 98 - You may need to run ``./mach clobber`` for your DLL to be recognized. 99 - You can compile your plugin in debug mode and step through it with a debugger by attaching to the installer/uninstall process. 100 - If libraries are needed, files in the ``$SRCDIR/mfbt/`` and ``$SRCDIR/toolkit/`` directories are usually okay although there may be exceptions. 101 - The best way to access headers is usually to simply copy them into the project given how disconnected this is from the rest of the build system.