daves Posted March 25, 2016 Share Posted March 25, 2016 Background We like to push the DT products to their limits. Our customers can currently write custom code of their own in a DLL which talks through our HMI. Feedback from the machine is passed to the DLL. The output from the DLL then modifies the command to the machine. Aim We want to move this custom module to the PPMAC (to improve performance etc). We cannot provide the source to the customer so it has to be an extension of the existing project. Proposals I have managed to write a new kernel module and call it from userservo. This works but is a hassle to set up and exposes too much stuff to the customer. I have also managed to compile user kernel code and link it to the existing usrcode.o and usralgomain.o files to make the useralgo.ko file and FTP it across. This works and is my preferred method. I think I understand the limitations of writing LKMs and realise the dangers of exposing this to customers but I cannot think of another way to extend functions called from userservo (we really want to run on the realtime core of a 465 card). Questions Does anyone else have experience of this? Advice? Can anyone see any pitfalls? Please can someone tell me how to stop/start the usralgo module? Currently I have to cycle the power every time I change my rebuilt module. I need to avoid this as the customer will need to easily swap between custom modules. I am awaiting DT assistance from an email but if any other users have experience this would be great. Link to comment Share on other sites More sharing options...
Omron Forums Support Posted March 25, 2016 Share Posted March 25, 2016 I am not sure what you mean by "extend" functions. If your main concern is hiding code from the customer, I suggest you encrypt your C code. See page 212 of the Power PMAC IDE manual for more details. Link to comment Share on other sites More sharing options...
shansen Posted March 25, 2016 Share Posted March 25, 2016 daves: My company has done something similar (allowed our customers to write code that gets compiled and run as user-phase code). Our approach was this: 1) Customer writes a function that conforms to our specifications 2) Customer compiles their function using a provided kernel module template (turns customer's function into a kernel module) 3) Customer uploads kernel module (.ko) to Power PMAC via FTP 4) We have a C-program that is constantly scanning the FTP folder for changes, and when it sees the new .ko it makes a copy of it to a safe location (so it can't be deleted while in use) and modprobe's it to install it in the kernel. 5) After modprobe'ing, our code searches /proc/kallsyms for the function name (provided by customer), and finds the address of this function. 6) This address is copied to pshm->Motor[#].UserPhase and pshm->UserAlgo.PhaseAddr[#], where # is the motor interrupt we want it to run in. We typically use motors that aren't actually running real hardware (e.g. virtual motors) for this purpose. 7) Our customer's kernel module is automatically called by Delta Tau's phase interrupt as user phase code. Our customer can have multiple kernel modules running code, and each one can run in a separate motor. 8) If the kernel module (.ko) file is removed from the folder, we disable the motor that is running that phase code and then clear the module out of memory. This lets our customer dynamically load/unload modules. This solution has some pitfalls (requires customer to have toolchain to compile), but other than that it works pretty well. Link to comment Share on other sites More sharing options...
daves Posted March 30, 2016 Author Share Posted March 30, 2016 Thank you very very much shansen. It is comforting to know someone else is doing this! I have followed your advice and now have a LKM I can rmmod/FTP/modprobe on the fly, locate the function address, and stuff into userservo. All using a background C-app reacting to a command from the HMI. I can supply our customers with some template code and a makefile along with the compilers/libraries (of the best way to do this I am unsure; I am waiting for a response about any distribution issues, also I assume this will need to be tied to a particular firmware release). Another question: Everything "works". My customer module calls some functions I export from the usralgo module (making them available between modules). However the build of the customer module warns these functions are undefined. I see Module.symvers is the key. Do you know much about it? I must admit I haven't looked into it much but have failed to get the makefile to use the module.symvers from the DT project on my first attempts. Thanks again Link to comment Share on other sites More sharing options...
shansen Posted March 30, 2016 Share Posted March 30, 2016 daves: Yes, you are absolutely right. To get rid of the "undefined function" warnings, you will need to edit the makefile for the customer's kernel module and add the path to the Module.symvers that was generated when you compiled your template kernel module. The path should be added to KBUILD_EXTRA_SYMBOLS. Something like this: Original: KBUILD_EXTRA_SYMBOLS := /Module.symvers Modified: KBUILD_EXTRA_SYMBOLS := /Module.symvers /Module.symvers Another trick: the reason to use 'modprobe' instead of 'insmod' is because modprobe will also install any dependencies if your module depends on others. But, to get this to work you have to: 1) Copy your kernel modules to "/lib/modules/$(uname -r)" 2) Issue a "depmod -a" (this searches /lib/modules/$(uname -r) for all kernel modules and figures out their dependencies) 3) Then issue "modprobe" for each .ko Link to comment Share on other sites More sharing options...
daves Posted March 31, 2016 Author Share Posted March 31, 2016 Thanks again I am floundering with this makefile/cygwin stuff (my ignorance I'm afraid). I cannot figure out how to get my Module.symvers easily found... I can do it if I set: KBUILD_EXTRA_SYMBOLS := /usr/local/dtlibs/libppmac/Module.symvers /usr/local/dtlibs/libppmac/Module2.symvers and copy my Module.symvers to "C:\DeltaTau\Power PMAC IDE\compilers\usr\local\dtlibs\libppmac" as Module2.symvers I cannot figure out how to get the path to it if it resides in a subfolder (mymod) off where the c files are (current directory running make from a Windows command window). I have messed around for ages with $(PWD), cygpath etc if I add stuff like the following (or any combination, or not at all!) WIN_MOD := $(shell cygpath -m -a mymod/Module.symvers) WIN_MOD := $(shell cygpath -u $(WIN_MOD)) ifneq ("$(wildcard $(WIN_MOD))","") FILE_EXISTS = 1 else FILE_EXISTS = 0 endif I always get the file reported as existing but not accepted in KBUILD_EXTRA_SYMBOLS. Maybe I just give up and do the copying thing above which works. It must be a cygwin/windows path issue but I am stuck. I do the /lib/modules/$(uname -r), depmod, and modprobe bits so it all works in terms of functioning. I just don't like the warning on make! Link to comment Share on other sites More sharing options...
shansen Posted March 31, 2016 Share Posted March 31, 2016 This is one of the reasons I no longer use Windows for compiling Power PMAC code! The Windows path handling in cygwin leaves much to be desired. Have you tried using "=" in your makefile instead of ":="? When you use ":=" it expands any $() variables at definition time instead of at runtime. Also, there is a way to redefine a Windows path into a cygwin path, so C:\Users\User\My Documents gets mapped to /somemountpoint, but I don't remember how off the top of my head. Or just edit your Module2 makefile to copy Module2.symvers to the correct location after it finishes compiling. Link to comment Share on other sites More sharing options...
daves Posted October 7, 2016 Author Share Posted October 7, 2016 Hi I have had this custom kernel module approach working at my customer's site well for these past months. I have two more customers wanting to use this feature so I have some urgent question s regarding distribution of DT libraries. I am going to end up with three customers with different versions of IDE and Firmware. The building of my custom module uses DT libraries (like the math functions) My current solution involves distributing the compilers.tar.gz, CompilerExtractProgress.exe files and extracttool folder from my PC to the customer and getting them to run CompilerExtractProgress.exe (I had the same IDE and firmware as the customer at that time). 1) Is this OK? 2) How do the libraries in that gz relate to the firmware on the card? 3) Are they just the libraries distributed with the IDE and not necessarily right for the customer’s firmware? 4) I know there is(was) a strange step in the IDE when first talking to a 465 where libraries are uploaded, is this an issue? 5) I know some files are uploaded by the IDE on a Build command, does the customer need these files (what are they)? 6) I envisage the customer building these modules on a PC not necessarily connected to the PPMAC card, is this possible? How to best proceed... Link to comment Share on other sites More sharing options...
steve.milici Posted October 10, 2016 Share Posted October 10, 2016 I will have one of the software engineers look into this. Link to comment Share on other sites More sharing options...
AnthonyLH Posted December 12, 2016 Share Posted December 12, 2016 Hello, I will also have to develop a kernel module, to build it and to fournish is to our customer. This kernel modul will contain the kinematic that should be called from the CfromScript (usercode.ko/so). It will really help me if one of you had an example/doc that could be shared. Thanks you! Link to comment Share on other sites More sharing options...
steve.milici Posted December 12, 2016 Share Posted December 12, 2016 The IDE has an example project (CFromScriptKinExample) of how to do this: C:\DeltaTau\Power PMAC IDE\PowerPMACProjectExamples\CfromScriptKinExample Link to comment Share on other sites More sharing options...
Recommended Posts