CopperD Posted February 17, 2016 Report Posted February 17, 2016 Name: DCG Submitter: CopperD Submitted: 16 Feb 2016 Category: *Uncertified* LabVIEW Version: Not ApplicableLicense Type: Creative Commons Attribution 3.0 Allows new functions to be compiled during runtime by using libtcc. http://bellard.org/tcc/ Features Full ANSI C compiler ISO C99 extensions (Missing only complex and imaginary numbers) GNU C extensions (See TCC Docs) TinyCC extensions (See TCC Docs) GNU-like inline assembler 32bit & 64bit opcodes depending on DLL (See TCC Docs) Compile to memory to call as function or disk as exe Allows for dynamic code Pointer safe checks Examples Adding 2 numbers and using return to get the result Using system to call cmd Inline x86 assembly Passing in information using argc and argv Using pointers to pass a string in and an SHA512 hash out Uses libtcc unmodified, so for security reasons you can download the dll from the author's website or compile your own from source. The dll is included if you wish to use it. Some very basic examples that show off only a tiny subset of the features this compiler offers. Unless you are very careful, compiling functions during runtime can lead to unstable code. (Test before you deploy) All examples should run without issue but modification can and will lead to crashing. (Save often) Click here to download this file Quote
ShaunR Posted February 18, 2016 Report Posted February 18, 2016 OK. So it is a thin wrapper around the Tiny C Compiler.(Note that TCC is LGPL licenced ) It looks like the "State" is an opaque pointer to a structure so you might want to choose "Unsigned Pointer-Sized Integer" so that it is 32 and 64 bit ready. I would also suggest putting each function in a case structure and checking for 0. You can't test a pointer in C to see if it exists so the best you can do is hope that the library returns null pointers when memory is released or memory can't be allocated. For your DSNewPtr, which is a LabVIEW function; there are already VIs for that and others. I forget whether they are under resources or in vi.lib but I think you should separate out LabVIEW functions and application specific functions. LabVIEW functions are reuseable and usually cross platform , whereas application specific ones are or may not be. Looking forward to being able to auto-compile libbitcoin from LabVIEW 2 Quote
CopperD Posted February 19, 2016 Author Report Posted February 19, 2016 (edited) These are going to all become private functions in the near future. I am only going to have a few functions available to the normal user. This is my general plan for a library. LV_DCG_Compile_String_Program.vi (Complete C program or Library going to disk as DLL ) (Overwrites if name is same as previous compiled code) Inputs Mode (Memory, Exe, Dll) required Program name/name of exe or dll (String) required Code (String) required Error in Outputs Error out (Set if not compiled and string with why) LV_DCG_Compile_String_Library.vi (Collection of functions) (Overwrites if name is same as previous compiled code) Inputs Library name (String) required Code (String) required Error in Outputs Error out (Set if not compiled and string with why) LV_DCG_List.vi (List compiled programs and library functions) Inputs Mode (Programs, Libraries, Library Functions, All Library Functions, All) Library Name (String) Error In Outputs Names (1D array of strings) (Programs names, libraries, or library functions in "Library_Name.Function_Name") Error Out LV_DCG_Run_Program.vi (Runs Programs using argc argv or none at all) Inputs name (String) required Arguments in (1d array of strings) Error in Outputs Program Return (int) Error out LV_DCG_Run_Function.vi (Requires the function prototype, return type, and data in) Inputs (I am thinking about this one) name (String) Required Return Size (int) Required Prototype and data (1D Array of Cluster(Data type(u8) ,value(var)) Error In Outputs Program Return (1d array of bytes of size return size) Error out LV_DCG_Manage.vi (Remove program, Remove Library, Remove All) I'll add preprocessor and other functions for adding dlls and such later. But I want it simple and sweet. No libbitcoin (C++) but libccoin or picocoin. I like the check for a zero on the pointer, that could save a lot of debug time. No clue why I used an int for the pointer. I see DSNewPtr and DSDisposePtr but no MoveBlock. I remember the GetValueByPointer xnode and being burned because it wouldn't compile. Hmmm it compiles now Still no poking unless you use moveblock. Do they have some look but don't touch policy at NI? This reminded me of Dr Cold hands at MEPS. We were told to bend down and spread em. Then Dr was going to take a peek and if the Dr didn't like what he saw he would take a poke. I have a dream that one day Call Library Function Node will accept function pointers rather than just a path. Edited February 19, 2016 by CopperD 1 Quote
ShaunR Posted February 19, 2016 Report Posted February 19, 2016 These are going to all become private functions in the near future. I am only going to have a few functions available to the normal user. This is my general plan for a library. <snip> Nice. We didn't need a spec, but since you've given us one - polymorphic VIs are great. I see DSNewPtr and DSDisposePtr but no MoveBlock. I remember the GetValueByPointer xnode and being burned because it wouldn't compile. Hmmm it compiles now Still no poking unless you use moveblock. Do they have some look but don't touch policy at NI? They never encapsulated Moveblock. I don't know why - it's the single most useful function for CLFNs. Call Library Function Node will accept function pointers rather than just a path. Tempting to wish for callback features but I'm ambivalent. If there is one good way to crash a LabVIEW program, it is to write some of it in another language. CLFNs are a last resort when no other options exists rather than standard coding practice. After all. If you want to write GPF ridden software, there are better languages like C and C++ Quote
CopperD Posted February 19, 2016 Author Report Posted February 19, 2016 C++ is such an awful bastardization of C. Unless you're being stupid setting the GPF interrupt is unlikely. Windows should handle this before you ever get to that level. Your program will still get killed but you don't need to worry about the CPU starting to wonder if it should halt. I was thinking about adding code to check where the page the pointer is in and its access permissions. Its extra overhead and training wheels so I don't know how I feel about it. Maybe a global flag in a list of options so it's only a jump if you don't want to perform the check. Quote
JKSH Posted February 20, 2016 Report Posted February 20, 2016 I was thinking about adding code to check where the page the pointer is in and its access permissions. Its extra overhead and training wheels so I don't know how I feel about it. Maybe a global flag in a list of options so it's only a jump if you don't want to perform the check. Perhaps you could let the user toggle between Debug mode and Release mode? Debug mode performs checks and flashes big angry warnings if a violation is found; Release mode assumes that the developer has already combed through their code using Debug mode, so it skips the checks. 1 Quote
CopperD Posted February 20, 2016 Author Report Posted February 20, 2016 Perhaps you could let the user toggle between Debug mode and Release mode? Debug mode performs checks and flashes big angry warnings if a violation is found; Release mode assumes that the developer has already combed through their code using Debug mode, so it skips the checks. That is a great idea, I'm going to do that. Now a little extra information just so I can picture ShaunR cringle. Once TCC has compiled the program I copy the compiled code into an empty pointer from DSNewPtr of compiled function size. I also get the starting location of main for the program. Next the memory space is set executable. Finally when you want to run the program we call it as a function pointer. If only we had a good way of doing this inside LabVIEW without resorting to a buffer overflow. My options currently are using a small program in TCC or libffi. Libffi would be very useful in the future and for other projects. Quote
CopperD Posted February 29, 2016 Author Report Posted February 29, 2016 (edited) I really want this to turn your code from a nice solid block of steel into something with the constancy of runny applesauce. Feature Creep! PE32/+ Analysis Emulated PE32/+ loader (Why limit yourself to code you have source for?)​Performs memory allocations and base relocation Run exe applications internally Call dll functions internally I'll be posting this update sometime this week. Edited February 29, 2016 by CopperD Quote
CopperD Posted April 25, 2016 Author Report Posted April 25, 2016 (edited) I have been mostly away on vacation and loaded with work for the last month and a half. However some progress has been made. An update showing off some of this will be put up in the next week or two. PE Loader Progress Load and execute exe from memory if ImageBase does not conflict- 95% (FInishing up some debugging on the Import Directory) Load and execute exe from memory with conflicted ImageBase but has Relocation Table - (75% ) Load DLL from memory and call functions - (65% need to finish work with Relocation Table and add code to call DLL Entry Point) Load and execute exe from memory with conflicted ImageBase but has no Relocation Table - (20% I have only generated a Relocation Table by hand with the help of a disassembler) May need to attach the Titan or Bea Engine for disassembly. Load and inject exe from memory regardless of ImageBase as a new process - (60% This might raise some red flags - more of an experiment) Dynamic Function Calls Support for __stdcall __fastcall __cdecl (40% Little bit of bytecode that uses a pointer to cluster of the function prototype passed in from createThead to launch your function) Function Pointers Windows API createThread (100% IDE not aware of new threads - Wrapped so you can wait for thread to return or continue without waiting) LabVIEW API THThreadCreate (70% Decoded function prototype and can use it to call function pointers - Need to figure out how this is being used internally so IDE can be aware of the new threads) SmashCall (90% Works but needs some bytecode added to clean up the mess it creates - Another experiment) The above items are being used to support code generated by LibTCC and the embedding of LibTCC and its supporting files. I promise this all ties together and goes somewhere. Edited April 25, 2016 by CopperD Quote
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.