News:

Masm32 SDK description, downloads and other helpful links
Message to All Guests
NB: Posting URL's See here: Posted URL Change

Main Menu

Using 32-bit code in 64-bit land

Started by jj2007, March 10, 2017, 03:42:45 PM

Previous topic - Next topic

hutch--

For secure inter app communication you use a private message that is unique to your app and the other you are communicating with.

invoke PostMessage,HWND_BROADCAST,PM_YOURMESSAGE,0,0

jj2007

On topic: Does anybody have experience with ZwExtendSection? Apparently, it's the only way to implement a realloc on a memory-mapped file, but it's kind of undocumented...

hutch--

With a bit of messing around you could do this with the existing capacity without having to go to risky undocumented functions. Use messaging to tell both apps to shut down the existing MMF, send another message with the new size then send a message telling both to create a new MMF. Written properly it would work OK and probably be easily fast enough.

jj2007

Complicated. Here is a shorter option:
mov rax, 8000000000
jinvoke CreateFileMapping, INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, rax, Chr$("~TmpObject")


Works fine and returns immediately.

adeyblue

Quote from: jj2007 on March 14, 2017, 01:10:05 AM
On topic: Does anybody have experience with ZwExtendSection? Apparently, it's the only way to implement a realloc on a memory-mapped file, but it's kind of undocumented...

It basically does this part of the CreateFileMapping documentation, but on demand.
Quote
If an application specifies a size for the file mapping object that is larger than the size of the actual named file on disk, the file on disk is increased to match the specified size of the file mapping object

It is only for mapped disk files that you've opened for writing. It'll fail if you instead pass NULL as the file handle to CreateFileMapping. Here's an example.


#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <stdio.h>

extern "C"
DECLSPEC_IMPORT
long
WINAPI
NtExtendSection(HANDLE hMap, PLARGE_INTEGER pNewSize);

int main()
{
HANDLE hFile = CreateFileW(L"file.txt", GENERIC_ALL, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_TEMPORARY | FILE_FLAG_DELETE_ON_CLOSE, NULL);
if(hFile == INVALID_HANDLE_VALUE) {return printf("CreateFile fail - error %lu!\n", GetLastError());}
SetFilePointer(hFile, 1, NULL, FILE_BEGIN); // You can't map a 0 length file
SetEndOfFile(hFile);
DWORD size = GetFileSize(hFile, NULL);
printf("Original file size is %lu\n", size);
HANDLE hMapping = CreateFileMapping(hFile, NULL, PAGE_READWRITE, 0, 8192, NULL);
if(hMapping == NULL) {return printf("CreateFileMapping fail - error %lu!\n", GetLastError());}
size = GetFileSize(hFile, NULL);
printf("After CreateFileMapping, file size is %lu\n", size);
HANDLE hAllPermHandle = NULL;
// docs lie, CreateFileMapping doesn't create an all access handle
// it doesn't have SECTION_EXTEND_SIZE right which is required for NtExtendSection
// without this, NtExtendSection will fail with 0xc0000022 (STATUS_ACCESS_DENIED)
DuplicateHandle(GetCurrentProcess(), hMapping, GetCurrentProcess(), &hAllPermHandle, SECTION_ALL_ACCESS, FALSE, DUPLICATE_CLOSE_SOURCE);
if(hAllPermHandle == NULL) {return printf("DuplicateHandle fail - error %lu!\n", GetLastError());}
hMapping = hAllPermHandle;
PVOID pMapping = MapViewOfFile(hMapping, FILE_MAP_WRITE, 0, 0, 0);
if(pMapping == NULL) {return printf("MapFileMapping fail - error %lu!\n", GetLastError());}
MEMORY_BASIC_INFORMATION mbi = {0};
VirtualQuery(pMapping, &mbi, sizeof(mbi));
printf("Mapped size is %Iu\n", mbi.RegionSize);

LARGE_INTEGER newSize = {16384};
long stat = NtExtendSection(hMapping, &newSize);
if(stat < 0) {return printf("NtExtendSection fail - err %#x\n", stat);}
size = GetFileSize(hFile, NULL);
printf("After NtExtendSection file size is %lu\n", size);
VirtualQuery(pMapping, &mbi, sizeof(mbi));
        // It doesn't update the mapped memory size though, you have to map any new bits yourself
printf("Mapped size after NtExtendSection is %Iu\n", mbi.RegionSize);
}


jj2007

Quote from: adeyblue on March 14, 2017, 10:37:48 AMIt'll fail if you instead pass NULL as the file handle to CreateFileMapping.

You mean -1, INVALID_HANDLE_VALUE?

jj2007

Just for fun, attached a 64-bit application that calls a 32-bit server which translates Windows.inc into a string array using Recall. The 64-bit program prints the first n strings of the array to the console.

To test it, extract all files to a folder and start GetStringsFrom32BitLib.exe; afterwards, press O (like open) to see the first 39 strings and timings. For me (Core i5), it's around 100 ticks with printing 33 lines, and around 8 ticks when printing only one line (see source, line 93, .Until ct>32). Task manager looks OK, even if I keep the "O" pressed.

Every time you "open" the file, a 800MB MMF gets created (and closed):
   mov rax, 800000000
   jinvoke CreateFileMapping, INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, rax, Chr$("~TmpObject")

adeyblue

Quote from: jj2007 on March 14, 2017, 11:16:43 AM
Quote from: adeyblue on March 14, 2017, 10:37:48 AMIt'll fail if you instead pass NULL as the file handle to CreateFileMapping.

You mean -1, INVALID_HANDLE_VALUE?

NULL is accepted as -1 (or rather -1 is converted to NULL), so they're equivalent for CreateFileMapping.

jj2007

Quote from: adeyblue on March 15, 2017, 04:57:48 AMNULL is accepted as -1 (or rather -1 is converted to NULL)

You have hacked the CreateFileMapping source :eusa_naughty:

Under the hood, 000007FEFD3F19D2:
000007FEFD3F19C4 | 4C 8D 4C 24 40                       | lea r9, qword ptr ss:[rsp+40]                 |
000007FEFD3F19C9 | 89 44 24 40                          | mov dword ptr ss:[rsp+40], eax                |
000007FEFD3F19CD | 44 89 6C 24 44                       | mov dword ptr ss:[rsp+44], r13d               |
000007FEFD3F19D2 | 48 83 FD FF                          | cmp rbp, FFFFFFFFFFFFFFFF                     |
000007FEFD3F19D6 | 0F 84 C4 00 00 00                    | je 7FEFD3F1AA0                                |
@@:
000007FEFD3F19DC | 83 FE FF                             | cmp esi, FFFFFFFF                             |
000007FEFD3F19DF | 0F 85 23 D5 00 00                    | jne 7FEFD3FEF08                               |
...
000007FEFD3F1AA0 | 4D 85 C9                             | test r9, r9                                   |
000007FEFD3F1AA3 | 0F 84 E5 D3 00 00                    | je 7FEFD3FEE8E                                |
000007FEFD3F1AA9 | 33 ED                                | xor ebp, ebp                                  |
000007FEFD3F1AAB | E9 2C FF FF FF                       | jmp @B   ;7FEFD3F19DC                               |


So -1 and 0 work - and no other value :t

Slightly odd the test r9, r9 at AA0; there is no such test if you pass handle zero, and with the lea r9, [rsp+40], it can never be zero ::)

Btw this is the limit on my 4GB RAM machine - slightly under one GB:
mov rax, 1020000000
jinvoke CreateFileMapping, -1, NULL, PAGE_READWRITE, 0, rax, Chr$("~TmpObject")

jj2007

Quote from: jj2007 on March 13, 2017, 08:32:59 PMHow many times did they try to discourage people from using DDE ("Atoms and Shared Memory Objects")? It still works with Micros**t Office...

EDIT: Apparently, DDE does no longer work with Excel 2016:
QuoteAnonymous commented  ยท  January 12, 2017

I agree with anonymous October 6, 2016. Mail merge is now a nightmare!

Users trying to blackmail Micros**t ("If it is not included we never update our office Package to a newer Version in the whole company"): 47 comments (and M$ regularly deletes older comments). Yeah, long live DDE :t

jj2007

Is mov rax, [ebx] possible? Test yourself...
include \Masm32\MasmBasic\Res\JBasic.inc
Init ; OPT_64 1 ; put 0 for 32 bit, 1 for 64 bit assembly
  push rax ; keep align 16
  push 11111111h
  mov rbx, rsp
  mov eax, [ebx]
  Print Str$("eax=%x\n", eax) ; result: 11111111h
  add rsp, SIZE_P*2
  push rax ; keep align 16
  push 22222222h
  mov rbx, rsp
  mov rax, [ebx] ; <<<<<<<<<<<<<<
  Inkey Str$("rax=%x\n", rax) ; result: 22222222h
  add rsp, SIZE_P*2
EndOfCode


felipe

Don't know. Seems like that Init and others expand to a lot of code...You know, i'm just guessing... :idea:


jj2007

Quote from: felipe on June 06, 2018, 04:37:16 AMDon't know. ... just guessing
Why do you post if you don't know anything, and are just guessing? To increase your post count? You won't get a banana if you reach your 1,000 posts. Concentrate on your code, and eliminate your bugs, Felipe.

felipe

Quote from: jj2007 on June 06, 2018, 05:46:04 AM
Why get a banana if you reach 1,000. Concentrate on your bugs, Felipe.

You are right.  :icon14:

sinsi

> Is mov rax, [ebx] possible?
Even mov rax,[bx] is possible, as long as bx points to valid memory (hint: it doesn't in most modern OSes).