How can I make Russian letters visible in a IUP dialog loaded from a LED file? - iup

How can I make Russian letters visible in a dialog loaded from a LED file?
When the LED file is Unicode, IupLoad() returns an error.
When the LED file is UTF-8, IUP believes it has loaded and
shown the dialog but there is only vacuum.
When the LED file is ANSI, we get the predictable result:
(Ignore the red box, I’ve placed it there for another question.)
C file:
#include <stdlib.h>
#include <iup.h>
int main(int argc, char **argv)
{
IupSetGlobal("UTF8MODE", "YES");
// IupSetGlobal("UTF8MODE_FILE", "YES");
IupOpen(&argc, &argv);
if(IupLoad("dropdown.led")) IupMessage("Error", "Failed to load LED.");
else {
Ihandle *dropdown = IupGetHandle("dropdown");
IupShow(dropdown);
IupMainLoop();
}
IupClose();
return EXIT_SUCCESS;
}
Accompanying dropdown.led file:
dropdown = DIALOG[TITLE=dropdown.led](
HBOX[CMARGIN=10x10,CGAP=10](
LIST[VALUE=3, 1=я, 2=ты, 3=оно, 4=мы, 5=вы, 6=они, DROPDOWN=YES](do_nothing),
LIST[VALUE=3, 1=ik, 2=je, 3=hij, 4=we, DROPDOWN=YES](do_nothing)
)
)
Update: an experiment with manual LED file loading
I have attempted a workaround in the form of loading the LED file manually (my function LoadLED() below) and replacing IupLoad() with IupLoadBuffer(). However this has failed too, albeit – oddly enough – in reverse:
When the LED file is Unicode, IUP believes it has loaded and
shown the dialog but there is only vacuum.
When the LED file is UTF-8, IupLoadBuffer() returns an error.
IupLoadBuffer() reverses the faulty undesirable behaviour of IupLoad() regarding UTF-8 and Unicode – but it’s faulty not the desired outcome still.
IupMessage() confirms that UTF-8 mode is in force: it displays Russian letters in the LED file (UTF-8) correctly. It demonstrates that the problem is localised in the IupLoad() and IupLoadBuffer() functions rather than something caused by my incompetence. (In the end, it was kind of neither: the functions work as intended but I had no way of knowing the specific conditions necessary to make them work.)
Modified C file:
#include <stdio.h>
#include <stdlib.h>
#include <iup.h>
char *LoadLED(char *buffer, size_t size, char *ledFileName) {
FILE *led;
if (led = fopen(ledFileName, "rb")) /* Binary mode for UTF-8! */ {
fread(buffer, 1L, size, led);
fclose(led);
IupMessage("Loaded LED file", buffer);
return buffer;}
else return IupMessage("Error", "Failed to load LED."), NULL;
}
int main(int argc, char **argv) {
IupSetGlobal("UTF8MODE", "YES");
IupSetGlobal("UTF8MODE_FILE", "YES");
IupOpen(&argc, &argv);
char buffer[20000L], ledFileName[] = "dropdown.led";
if (!LoadLED(buffer, sizeof(buffer), ledFileName)) return EXIT_FAILURE;
if (IupLoadBuffer(buffer))
return IupMessage("Error", "Failed to load buffer."), EXIT_FAILURE;
else {
Ihandle *dropdown = IupGetHandle("dropdown");
IupShow(dropdown);
IupMessage("Success", "IUP thinks it has loaded buffer and displayed dialog.");
IupMainLoop();
}
return IupClose(), EXIT_SUCCESS;
}
All questions that pertain to this particular example:
How do I get access to GUI elements in a IUP dialog loaded from a LED file?
How can I make Russian letters visible in a IUP dialog loaded from a LED file? (current)
A gap in IUP dropdown lists

First, IUP does NOT supports Unicode. So to test it is useless.
UTF8MODE_FILE is for file names. Does not affect this case.
The UTF-8 string maybe affecting the LED parser although they shouldn't. Make sure the LED file does NOT have the UTF-8 BOM. I tested here your LED file and it works using IupLoad or IupLoadBuffer, but in both cases there are problems with the strings.
The solution is actually simple, just wrap your strings with quotes "", for instance:
LIST[VALUE=3, 1="я", 2="ты", 3="оно", 4="мы", 5="вы", 6="они", DROPDOWN=YES](do_nothing),
It works.

Related

Unexpected value appears on stack when attempting buffer overflow

I am trying to learn more about cyber security, in this case about buffer overflows. I have a simple code that I want to change flow of:
#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>
#include <string.h>
void win()
{
printf("code flow successfully changed\n");
}
int main(int argc, char **argv)
{
volatile int (*fp)();
char buffer[64];
fp = 0;
gets(buffer);
if(fp) {
printf("calling function pointer, jumping to 0x%08x\n", fp);
fp();
}
}
By using some tools I have determined that function pointer (fp) gets it value updated after 72 characters have entered the buffer. The function win() is located at value 0xe5894855 so after 72 characters I need to provide that value to buffer for it to jump to the desired function.
However I am facing this issue:
By putting Python3's print("A"*18*4 + "UH" + "\x89" + "\xe5") into input of given C code, I should be getting desired value 0xe5894855 in section marked with red. But instead, I am getting highlighted malformed hex from somewhere. (89 is getting extra C2 and incorrect e5 value is overflowing to next part of stack) (value in those parts of stack are zero initially, but changed into that once overflow is attempted).
Why is this happening? Am I putting hex values into C program incorrectly?
Edit: Still have not figured out why passing hex through python did not work, but I found a different method, by using Perl: perl -e 'print "A"x4x18 . "\x55\x48\x89\xe5"', which did work, and address I needed to jump to was also incorrect (which I also fixed)

MFC - Display message

I'm trying to display a simple message within my first MFC application.
Strangely, the first sample doesn't work, instead the second one works correctly.
auto text = std::to_wstring(1).c_str();
MessageBox(text, NULL, 0); // Not ok, the message is empty
auto temp = std::to_wstring(1);
MessageBox(temp.c_str(), NULL, 0); // Ok, display 1
Can you explain why of this behavior?
Yes, in the first example, the wstring created by the call to std::to_wstring only has the scope of the line. After the line executes, it is out of scope and its value is dubious.
In the second example, the wstring is still in scope and valid and so the call to .c_str() works.
No, the other answer is wrong. Look at the implementation of c_str(). c_str() returns basically a LPCWSTR... call it a const WCHAR* or const wchar_t* or whatever. However, the return of c_str() is to an internal pointer of wstring. The problem is that after the line of code executes, the wstring returned from to_wstring() is not valid and so the the pointer returned by c_str() is garbage. For fun, try the following code:
//cstr_.cpp
#include <iostream>
#include <string>
using namespace std;
int main(int argc, char* argv)
{
auto temp = to_wstring(1).c_str();
wprintf(L"%s\n", temp);
auto temp2 = to_wstring(1);
wprintf(L"%s\n", temp2.c_str());
wstring ws = to_wstring(1);
auto temp3 = ws.c_str();
wprintf(L"%s\n", temp3);
}
I compiled the above from a VC++ shell prompt with: cl.exe cstr.cpp
If the other answer is correct, then the last line should have garbage or nothing output because according to the other answer, c_str() is a temp. But, if my answer is correct, then it should output 1 (which it does). If all else fails, look at the implementation source code.

getch() returns \377! instead of reading character

I am using Xcode and using the C language trying to understand how to use the Getch function to start a project. I copied some code someone had written as an example that should work, however instead of the code waiting for me to enter a character, it returns one for me:
#include <midi_lib.h> <---------- this needs to be here for later
#include <curses.h>
int main() {
keypad(stdscr, TRUE); /* I dont know if this is needed*/
char c;
puts("Enter a character\n");
c = getch();
printf("You just typed a %c! \n", c);
getch();
}
This is the output:
Enter a character
You just typed a \377!
It works if i use Getchar(), but i dont want to have to press enter.
I'm really new to coding so it maybe something simple, but i have no idea....
LT
Well, you didn't even initialize the Ncurses library with initscr().
There really are a lot of things you are missing, so I recommend you to read the Ncurses howto that explains you everything from initializing (e.g. what that keypad(stdscr, true) is) to input and a lot more.
Here's an example that works:
#include <ncurses.h>
int main()
{
int ch;
initscr();
cbreak();
noecho();
keypad(stdscr, TRUE);
ch = getch();
endwin();
printf("The key pressed is %d\n", ch);
}
Try this to get you started
#include <midi_lib.h> <---------- this needs to be here for later
#include <curses.h>
int main()
{
char c;
keypad(stdscr, TRUE); /* I dont know if this is needed*/
puts("Enter a character\n");
do {
c = getch();
} while (c == (char)-1);
printf("You just typed a %c! \n",c);
}
Note that getch() is constantly polling the keyboard for input, when there is
none, it will get -1 and retry until there is some in which case it will fall out of the while loop and continue.
This probably isn't how you should be coding this, but it does answer your question. The computer will act busy while it is constantly polling the keyboard.

How to convert a function address to a symbol

Let's say I have a program like this
// print-addresses.cpp
#include <stdio.h>
void foo() { }
void bar() { }
void moo() { }
int main(int argc, const char** argv) {
printf("%p\n", foo);
printf("%p\n", bar);
printf("%p\n", moo);
return 0;
}
It prints some numbers like
013510F0
013510A0
01351109
How do I convert those numbers back into the correct symbols? Effectively I'd like to be able to do this
print-addresses > address.txt
addresses-to-symbols < address.txt
And have it print
foo
bar
moo
I know this has something to do with the Debug Interface Access SDK but it's not entirely clear to me how I go from an address to a symbol.
This seems like exactly what you're looking for: Retrieving Symbol Information by Address. This uses DbgHelp.dll and relies on calling SymFromAddr. You have to do that (I think) from within the running application, or by reading in a minidump file.
You can also use the DIA, but the calling sequence is a bit more complicated. Call IDiaDataSource::loadDataForExe and IDiaDataSource::openSession to get an IDiaSession, then IDiaSession::getSymbolsByAddr to get IDiaEnumSymbolsByAddr. Then, IDiaEnumSymbolsByAddr::symbolByAddr will let you look up a symbol by address. There is also a way (shown in the example at the last link) to enumerate all symbols.
EDIT: This DIA sample application might be a good starting point for using DIA: http://msdn.microsoft.com/en-us/library/hd8h6f46%28v=vs.71%29.aspx . Particularly check out the parts using IDiaEnumSymbolsByAddr.
You could also parse the output of dumpbin, probably with /SYMBOLS or /DISASM option.
if you are in linux, you could try addr2line
addr2line addr -e execuablebin -f

Stack around the variable 'xyz' was corrupted

I'm trying to get some simple piece of code I found on a website to work in VC++ 2010 on windows vista 64:
#include "stdafx.h"
#include <windows.h>
int _tmain(int argc, _TCHAR* argv[])
{
DWORD dResult;
BOOL result;
char oldWallPaper[MAX_PATH];
result = SystemParametersInfo(SPI_GETDESKWALLPAPER, sizeof(oldWallPaper)-1, oldWallPaper, 0);
fprintf(stderr, "Current desktop background is %s\n", oldWallPaper);
return 0;
}
it does compile, but when I run it, I always get this error:
Run-Time Check Failure #2 - Stack around the variable 'oldWallPaper' was corrupted.
I'm not sure what is going wrong, but I noticed, that the value of oldWallPaper looks something like "C\0:\0\0U\0s\0e\0r\0s[...]" -- I'm wondering where all the \0s come from.
A friend of mine compiled it on windows xp 32 (also VC++ 2010) and is able to run it without problems
any clues/hints/opinions?
thanks
The doc isn't very clear. The returned string is a WCHAR, two bytes per character not one, so you need to allocate twice as much space otherwise you get a buffer overrun. Try:
BOOL result;
WCHAR oldWallPaper[(MAX_PATH + 1)];
result = SystemParametersInfo(SPI_GETDESKWALLPAPER,
_tcslen(oldWallPaper), oldWallPaper, 0);
See also:
http://msdn.microsoft.com/en-us/library/ms724947(VS.85).aspx
http://msdn.microsoft.com/en-us/library/ms235631(VS.80).aspx (string conversion)
Every Windows function has 2 versions:
SystemParametersInfoA() // Ascii
SystemParametersInfoW() // Unicode
The version ending in W is the wide character type (ie Unicode) version of the function. All the \0's you are seeing are because every character you're getting back is in Unicode - 16 bytes per character - the second byte happens to be 0. So you need to store the result in a wchar_t array, and use wprintf instead of printf
wchar_t oldWallPaper[MAX_PATH];
result = SystemParametersInfo(SPI_GETDESKWALLPAPER, MAX_PATH-1, oldWallPaper, 0);
wprintf( L"Current desktop background is %s\n", oldWallPaper );
So you can use the A version SystemParametersInfoA() if you are hell-bent on not using Unicode. For the record you should always try to use Unicode, however.
Usually SystemParametersInfo() is a macro that evaluates to the W version, if UNICODE is defined on your system.

Resources