Add plc-commands WIOP
This commit is contained in:
6
ecmc_plugin_grbl/.vscode/settings.json
vendored
6
ecmc_plugin_grbl/.vscode/settings.json
vendored
@@ -14,6 +14,10 @@
|
||||
"regex": "cpp",
|
||||
"tuple": "cpp",
|
||||
"type_traits": "cpp",
|
||||
"utility": "cpp"
|
||||
"utility": "cpp",
|
||||
"bitset": "cpp",
|
||||
"memory": "cpp",
|
||||
"random": "cpp",
|
||||
"future": "cpp"
|
||||
}
|
||||
}
|
||||
@@ -43,8 +43,8 @@ volatile uint8_t sys_rt_exec_accessory_override; // Global realtime executor bit
|
||||
// Start worker for socket read()
|
||||
void f_worker_read(void *obj) {
|
||||
if(!obj) {
|
||||
printf("%s/%s:%d: Error: Worker read thread ecmcGrbl object NULL..\n",
|
||||
__FILE__, __FUNCTION__, __LINE__);
|
||||
printf("%s/%s:%d: Error: Worker read thread ecmcGrbl object NULL..\n",
|
||||
__FILE__, __FUNCTION__, __LINE__);
|
||||
return;
|
||||
}
|
||||
ecmcGrbl * grblObj = (ecmcGrbl*)obj;
|
||||
@@ -98,9 +98,15 @@ ecmcGrbl::ecmcGrbl(char* configStr,
|
||||
|
||||
// Init
|
||||
cfgDbgMode_ = 0;
|
||||
cfgAutoStart_ = 0;
|
||||
destructs_ = 0;
|
||||
connected_ = 0;
|
||||
executeCmd_ = 0;
|
||||
resetCmd_ = 0;
|
||||
haltCmd_ = 0;
|
||||
resumeCmd_ = 0;
|
||||
errorCode_ = 0;
|
||||
ecmcError_ = 0;
|
||||
errorCodeOld_ = 0;
|
||||
exeSampleTimeMs_ = exeSampleTimeMs;
|
||||
cfgXAxisId_ = -1;
|
||||
cfgYAxisId_ = -1;
|
||||
@@ -124,6 +130,11 @@ ecmcGrbl::ecmcGrbl(char* configStr,
|
||||
autoEnableExecuted_ = 1;
|
||||
}
|
||||
|
||||
// auto execute
|
||||
if(cfgAutoStart_) {
|
||||
executeCmd_ = 1;
|
||||
}
|
||||
|
||||
// global varaible in grbl
|
||||
enableDebugPrintouts = cfgDbgMode_;
|
||||
|
||||
@@ -132,14 +143,14 @@ ecmcGrbl::ecmcGrbl(char* configStr,
|
||||
throw std::out_of_range("No valid axis choosen.");
|
||||
}
|
||||
|
||||
// Create worker thread for reading socket
|
||||
std::string threadname = "ecmc.grbl.read";
|
||||
if(epicsThreadCreate(threadname.c_str(), 0, 32768, f_worker_read, this) == NULL) {
|
||||
throw std::runtime_error("Error: Failed create worker thread for read().");
|
||||
}
|
||||
//// Create worker thread for reading socket
|
||||
//std::string threadname = "ecmc.grbl.read";
|
||||
//if(epicsThreadCreate(threadname.c_str(), 0, 32768, f_worker_read, this) == NULL) {
|
||||
// throw std::runtime_error("Error: Failed create worker thread for read().");
|
||||
//}
|
||||
|
||||
// Create worker thread for main grbl loop
|
||||
threadname = "ecmc.grbl.main";
|
||||
std::string threadname = "ecmc.grbl.main";
|
||||
if(epicsThreadCreate(threadname.c_str(), 0, 32768, f_worker_main, this) == NULL) {
|
||||
throw std::runtime_error("Error: Failed create worker thread for main().");
|
||||
}
|
||||
@@ -209,12 +220,18 @@ void ecmcGrbl::parseConfigStr(char *configStr) {
|
||||
cfgSpindleAxisId_ = atoi(pThisOption);
|
||||
}
|
||||
|
||||
// ECMC_PLUGIN_AUTO_ENABLE_AT_START_OPTION_CMD (1..ECMC_MAX_AXES)
|
||||
// ECMC_PLUGIN_AUTO_ENABLE_AT_START_OPTION_CMD
|
||||
if (!strncmp(pThisOption, ECMC_PLUGIN_AUTO_ENABLE_AT_START_OPTION_CMD, strlen(ECMC_PLUGIN_AUTO_ENABLE_AT_START_OPTION_CMD))) {
|
||||
pThisOption += strlen(ECMC_PLUGIN_AUTO_ENABLE_AT_START_OPTION_CMD);
|
||||
cfgAutoEnableAtStart_ = atoi(pThisOption);
|
||||
}
|
||||
|
||||
// ECMC_PLUGIN_AUTO_START_OPTION_CMD
|
||||
if (!strncmp(pThisOption, ECMC_PLUGIN_AUTO_START_OPTION_CMD, strlen(ECMC_PLUGIN_AUTO_START_OPTION_CMD))) {
|
||||
pThisOption += strlen(ECMC_PLUGIN_AUTO_START_OPTION_CMD);
|
||||
cfgAutoStart_ = atoi(pThisOption);
|
||||
}
|
||||
|
||||
pThisOption = pNextOption;
|
||||
}
|
||||
free(pOptions);
|
||||
@@ -223,22 +240,26 @@ void ecmcGrbl::parseConfigStr(char *configStr) {
|
||||
|
||||
// Read socket worker
|
||||
void ecmcGrbl::doReadWorker() {
|
||||
// simulate serial connection here (need mutex)
|
||||
printf("%s:%s:%d\n",__FILE__,__FUNCTION__,__LINE__);
|
||||
for(;;) {
|
||||
//while(serial_get_tx_buffer_count()==0) {
|
||||
// delay_ms(1);
|
||||
//}
|
||||
//printf("%c",ecmc_get_char_from_grbl_tx_buffer());
|
||||
delay_ms(100);
|
||||
}
|
||||
// // simulate serial connection here (need mutex)
|
||||
// if(cfgDbgMode_){
|
||||
// printf("%s:%s:%d\n",__FILE__,__FUNCTION__,__LINE__);
|
||||
// }
|
||||
// for(;;) {
|
||||
// //while(serial_get_tx_buffer_count()==0) {
|
||||
// // delay_ms(1);
|
||||
// //}
|
||||
// //printf("%c",ecmc_get_char_from_grbl_tx_buffer());
|
||||
// delay_ms(100);
|
||||
// }
|
||||
}
|
||||
|
||||
// Write socket worker
|
||||
void ecmcGrbl::doWriteWorker() {
|
||||
// simulate serial connection here (need mutex)
|
||||
std::string reply = "";
|
||||
printf("%s:%s:%d\n",__FILE__,__FUNCTION__,__LINE__);
|
||||
if(cfgDbgMode_){
|
||||
printf("%s:%s:%d\n",__FILE__,__FUNCTION__,__LINE__);
|
||||
}
|
||||
|
||||
// Wait for grbl startup string before send comamnds"['$' for help]"
|
||||
// basically flush buffer
|
||||
@@ -249,15 +270,21 @@ void ecmcGrbl::doWriteWorker() {
|
||||
char c = ecmc_get_char_from_grbl_tx_buffer();
|
||||
reply += c;
|
||||
if(c == '\n' &&
|
||||
reply.find(ECMC_PLUGIN_GRBL_GRBL_STARTUP_STRING) != std::string::npos ) {
|
||||
printf("GRBL READY FOR COMMANDS: %s\n",reply.c_str());
|
||||
break;
|
||||
reply.find(ECMC_PLUGIN_GRBL_GRBL_STARTUP_STRING) != std::string::npos ) {
|
||||
if(cfgDbgMode_){
|
||||
printf("GRBL READY FOR COMMANDS: %s\n",reply.c_str());
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// GRBL ready, now we can send comamnds
|
||||
for(;;) {
|
||||
if(grblCommandBuffer_.size() > grblCommandBufferIndex_ && getEcmcEpicsIOCState()==16 && autoEnableExecuted_) {
|
||||
if( (grblCommandBuffer_.size() > grblCommandBufferIndex_) &&
|
||||
getEcmcEpicsIOCState()==16 &&
|
||||
autoEnableExecuted_ &&
|
||||
executeCmd_) {
|
||||
|
||||
epicsMutexLock(grblCommandBufferMutex_);
|
||||
std::string command = grblCommandBuffer_[grblCommandBufferIndex_];
|
||||
|
||||
@@ -266,10 +293,13 @@ void ecmcGrbl::doWriteWorker() {
|
||||
while(serial_get_rx_buffer_available() <= strlen(command.c_str())+1) {
|
||||
delay_ms(1);
|
||||
}
|
||||
printf("Write command to grbl: %s\n",command.c_str());
|
||||
if(cfgDbgMode_){
|
||||
printf("Write command to grbl (command[%d] = %s)\n",
|
||||
grblCommandBufferIndex_,
|
||||
command.c_str());
|
||||
}
|
||||
ecmc_write_command_serial(strdup(command.c_str()));
|
||||
reply = "";
|
||||
grblCommandBufferIndex_++;
|
||||
reply = "";
|
||||
// Wait for reply!
|
||||
for(;;) {
|
||||
while(serial_get_tx_buffer_count()==0) {
|
||||
@@ -278,20 +308,31 @@ void ecmcGrbl::doWriteWorker() {
|
||||
char c = ecmc_get_char_from_grbl_tx_buffer();
|
||||
reply += c;
|
||||
if(c == '\n'&& reply.length() > 1) {
|
||||
if(reply.find(ECMC_PLUGIN_GRBL_GRBL_OK_STRING) != std::string::npos) {
|
||||
printf("GRBL Reply: OK: %s\n",reply.c_str());
|
||||
if(reply.find(ECMC_PLUGIN_GRBL_GRBL_OK_STRING) != std::string::npos) {
|
||||
if(cfgDbgMode_){
|
||||
printf("GRBL Reply: OK (command[%d] = %s)\n",
|
||||
grblCommandBufferIndex_,
|
||||
command.c_str());
|
||||
}
|
||||
break;
|
||||
} else if(reply.find(ECMC_PLUGIN_GRBL_GRBL_ERR_STRING) != std::string::npos) {
|
||||
printf("GRBL Reply: ERROR: %s (%s)\n",reply.c_str(),command.c_str());
|
||||
if(cfgDbgMode_){
|
||||
printf("GRBL Reply: ERROR (command[%d] = %s)\n",
|
||||
grblCommandBufferIndex_,
|
||||
command.c_str());
|
||||
}
|
||||
errorCode_ = ECMC_PLUGIN_GRBL_COMMAND_ERROR_CODE;
|
||||
// Stop Motion here!!
|
||||
break;
|
||||
} else {
|
||||
// keep waiting (no break)
|
||||
printf("GRBL Reply: Non protocol: %s\n",reply.c_str());
|
||||
if(cfgDbgMode_){
|
||||
printf("GRBL Reply: Non protocol related: %s\n",reply.c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
grblCommandBufferIndex_++;
|
||||
}
|
||||
else {
|
||||
delay_ms(5);
|
||||
@@ -301,7 +342,9 @@ void ecmcGrbl::doWriteWorker() {
|
||||
|
||||
// Main grbl worker (copied from grbl main.c)
|
||||
void ecmcGrbl::doMainWorker() {
|
||||
printf("%s:%s:%d\n",__FILE__,__FUNCTION__,__LINE__);
|
||||
if(cfgDbgMode_){
|
||||
printf("%s:%s:%d\n",__FILE__,__FUNCTION__,__LINE__);
|
||||
}
|
||||
|
||||
// Initialize system upon power-up.
|
||||
serial_init(); // Setup serial baud rate and interrupts
|
||||
@@ -373,36 +416,28 @@ void ecmcGrbl::doMainWorker() {
|
||||
if(destructs_) {
|
||||
return;
|
||||
}
|
||||
printf("********************after protocol_main_loop()********************************\n");
|
||||
if(cfgDbgMode_){
|
||||
printf("********************after protocol_main_loop()********************************\n");
|
||||
}
|
||||
delay_ms(1);
|
||||
}
|
||||
}
|
||||
|
||||
void ecmcGrbl::autoEnableAtStart() {
|
||||
void ecmcGrbl::autoEnableAxisAtStart(int ecmcAxisId) {
|
||||
|
||||
if(!cfgAutoEnableAtStart_ || autoEnableExecuted_ || getEcmcEpicsIOCState()!=16) {
|
||||
return;
|
||||
}
|
||||
|
||||
// write to ecmc
|
||||
if(cfgXAxisId_>=0) {
|
||||
setAxisEnable(cfgXAxisId_,1);
|
||||
}
|
||||
if(cfgYAxisId_>=0) {
|
||||
setAxisEnable(cfgYAxisId_,1);
|
||||
}
|
||||
if(cfgZAxisId_>=0) {
|
||||
setAxisEnable(cfgZAxisId_,1);
|
||||
}
|
||||
|
||||
if(getAllConfiguredAxisEnabled()) {
|
||||
autoEnableExecuted_ = 1;
|
||||
}
|
||||
if(ecmcAxisId>=0) {
|
||||
setAxisEnable(ecmcAxisId,1);
|
||||
}
|
||||
}
|
||||
|
||||
bool ecmcGrbl::getEcmcAxisEnabled(int axis) {
|
||||
bool ecmcGrbl::getEcmcAxisEnabled(int ecmcAxisId) {
|
||||
int ena=0;
|
||||
getAxisEnabled(axis, &ena);
|
||||
getAxisEnabled(ecmcAxisId, &ena);
|
||||
return ena;
|
||||
}
|
||||
|
||||
@@ -430,50 +465,71 @@ double ecmcGrbl::getEcmcAxisActPos(int axis) {
|
||||
return pos;
|
||||
}
|
||||
|
||||
void ecmcGrbl::syncPositionIfNotEnabled() {
|
||||
void ecmcGrbl::preExeAxes() {
|
||||
preExeAxis(cfgXAxisId_,X_AXIS);
|
||||
preExeAxis(cfgYAxisId_,Y_AXIS);
|
||||
preExeAxis(cfgZAxisId_,Z_AXIS);
|
||||
//spindle
|
||||
autoEnableAxisAtStart(cfgSpindleAxisId_);
|
||||
if(getAllConfiguredAxisEnabled()) {
|
||||
autoEnableExecuted_ = 1;
|
||||
}
|
||||
}
|
||||
|
||||
void ecmcGrbl::preExeAxis(int ecmcAxisId, int grblAxisId) {
|
||||
syncAxisPositionIfNotEnabled(ecmcAxisId, grblAxisId);
|
||||
autoEnableAxisAtStart(ecmcAxisId);
|
||||
}
|
||||
|
||||
void ecmcGrbl::syncAxisPositionIfNotEnabled(int ecmcAxisId, int grblAxisId) {
|
||||
// sync positions when not enabled
|
||||
bool sync = 0;
|
||||
if(cfgXAxisId_>=0) {
|
||||
if(!getEcmcAxisEnabled(cfgXAxisId_)) {
|
||||
sys_position[X_AXIS] = (int32_t)(double(settings.steps_per_mm[X_AXIS])*getEcmcAxisActPos(cfgXAxisId_));
|
||||
sync = 1;
|
||||
}
|
||||
}
|
||||
if(cfgYAxisId_>=0) {
|
||||
if(!getEcmcAxisEnabled(cfgYAxisId_)) {
|
||||
sys_position[Y_AXIS] = (int32_t)(double(settings.steps_per_mm[Y_AXIS])*getEcmcAxisActPos(cfgYAxisId_));
|
||||
sync = 1;
|
||||
}
|
||||
}
|
||||
if(cfgZAxisId_>=0) {
|
||||
if(!getEcmcAxisEnabled(cfgZAxisId_)) {
|
||||
sys_position[Z_AXIS] = (int32_t)(double(settings.steps_per_mm[Z_AXIS])*getEcmcAxisActPos(cfgZAxisId_));
|
||||
sync = 1;
|
||||
}
|
||||
if(ecmcAxisId<0) {
|
||||
return;
|
||||
}
|
||||
|
||||
if(!getEcmcAxisEnabled(ecmcAxisId)) {
|
||||
sys_position[grblAxisId] = (int32_t)(double(settings.steps_per_mm[grblAxisId])*getEcmcAxisActPos(ecmcAxisId));
|
||||
sync = 1;
|
||||
}
|
||||
|
||||
if(sync) {
|
||||
plan_sync_position();
|
||||
gc_sync_position();
|
||||
}
|
||||
}
|
||||
|
||||
// prepare for rt here
|
||||
int ecmcGrbl::enterRT() {
|
||||
int ecmcGrbl::enterRT() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
// grb realtime thread!!!
|
||||
int ecmcGrbl::grblRTexecute(int ecmcError) {
|
||||
|
||||
if(ecmcError) {
|
||||
//Stop motion here!!!
|
||||
if(getEcmcEpicsIOCState()!=16) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if((ecmcError_ == 0 && ecmcError>0) || (errorCode_>0 && errorCodeOld_ == 0)) {
|
||||
setHalt(0);
|
||||
setHalt(1);
|
||||
setReset(0);
|
||||
setReset(1);
|
||||
setExecute(0);
|
||||
printf("Error encountered: ecmc 0x%x, plugin 0x%x\n",ecmcError,errorCode_);
|
||||
ecmcError_ = ecmcError;
|
||||
errorCodeOld_ = errorCode_;
|
||||
return errorCode_;
|
||||
}
|
||||
|
||||
syncPositionIfNotEnabled();
|
||||
autoEnableAtStart();
|
||||
ecmcError_ = ecmcError;
|
||||
errorCodeOld_ = errorCode_;
|
||||
|
||||
//auto enable, sync positions
|
||||
preExeAxes();
|
||||
|
||||
double sampleRateMs = 0.0;
|
||||
|
||||
if(grblInitDone_ && autoEnableExecuted_) {
|
||||
while(timeToNextExeMs_ < exeSampleTimeMs_ && sampleRateMs >= 0) {
|
||||
sampleRateMs = ecmc_grbl_main_rt_thread();
|
||||
@@ -487,25 +543,59 @@ int ecmcGrbl::grblRTexecute(int ecmcError) {
|
||||
timeToNextExeMs_-= exeSampleTimeMs_;
|
||||
}
|
||||
}
|
||||
// write to ecmc
|
||||
if(cfgXAxisId_>=0) {
|
||||
setAxisExtSetPos(cfgXAxisId_,double(sys_position[X_AXIS])/double(settings.steps_per_mm[X_AXIS]));
|
||||
}
|
||||
if(cfgYAxisId_>=0) {
|
||||
setAxisExtSetPos(cfgYAxisId_,sys_position[Y_AXIS]/settings.steps_per_mm[Y_AXIS]);
|
||||
}
|
||||
if(cfgZAxisId_>=0) {
|
||||
setAxisExtSetPos(cfgZAxisId_,sys_position[Z_AXIS]/settings.steps_per_mm[Z_AXIS]);
|
||||
}
|
||||
// if(cfgSpindleAxisId_>=0) {
|
||||
// setAxisTargetVel(xxx);
|
||||
// }
|
||||
|
||||
//update setpoints
|
||||
postExeAxes();
|
||||
return errorCode_;
|
||||
}
|
||||
|
||||
//void ecmcGrbl::setExecute(int execute) {
|
||||
//
|
||||
//}
|
||||
void ecmcGrbl::postExeAxis(int ecmcAxisId, int grblAxisId) {
|
||||
if(ecmcAxisId>=0) {
|
||||
setAxisExtSetPos(ecmcAxisId,double(sys_position[grblAxisId])/double(settings.steps_per_mm[grblAxisId]));
|
||||
}
|
||||
}
|
||||
|
||||
void ecmcGrbl::postExeAxes() {
|
||||
postExeAxis(cfgXAxisId_,X_AXIS);
|
||||
postExeAxis(cfgYAxisId_,Y_AXIS);
|
||||
postExeAxis(cfgZAxisId_,Z_AXIS);
|
||||
// if(cfgSpindleAxisId_>=0) {
|
||||
// setAxisTargetVel(xxx);
|
||||
// }
|
||||
}
|
||||
|
||||
// trigg start of g-code
|
||||
int ecmcGrbl::setExecute(int exe) {
|
||||
if(!executeCmd_ && exe) {
|
||||
//
|
||||
}
|
||||
executeCmd_ = exe;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ecmcGrbl::setHalt(int halt) {
|
||||
if(!haltCmd_ && halt) {
|
||||
//suspend with a "CMD_FEED_HOLD" command maybe?
|
||||
}
|
||||
haltCmd_ = halt;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ecmcGrbl::setResume(int resume) {
|
||||
if(!resumeCmd_ && resume) {
|
||||
//hepp
|
||||
}
|
||||
resumeCmd_ = resume;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ecmcGrbl::setReset(int reset) {
|
||||
if(!resetCmd_ && reset) {
|
||||
mc_reset();
|
||||
}
|
||||
resetCmd_ = reset;
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Avoid issues with std:to_string()
|
||||
std::string ecmcGrbl::to_string(int value) {
|
||||
@@ -515,9 +605,13 @@ std::string ecmcGrbl::to_string(int value) {
|
||||
}
|
||||
|
||||
void ecmcGrbl::addCommand(std::string command) {
|
||||
printf("%s:%s:%d:\n",__FILE__,__FUNCTION__,__LINE__);
|
||||
if(cfgDbgMode_){
|
||||
printf("%s:%s:%d:\n",__FILE__,__FUNCTION__,__LINE__);
|
||||
}
|
||||
epicsMutexLock(grblCommandBufferMutex_);
|
||||
grblCommandBuffer_.push_back(command.c_str());
|
||||
epicsMutexUnlock(grblCommandBufferMutex_);
|
||||
printf("%s:%s:%d: Buffer size %d\n",__FILE__,__FUNCTION__,__LINE__,grblCommandBuffer_.size());
|
||||
if(cfgDbgMode_){
|
||||
printf("%s:%s:%d: Buffer size %d\n",__FILE__,__FUNCTION__,__LINE__,grblCommandBuffer_.size());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -40,39 +40,52 @@ class ecmcGrbl : public asynPortDriver {
|
||||
double exeSampelTimeMs);
|
||||
~ecmcGrbl();
|
||||
|
||||
void doReadWorker();
|
||||
void doMainWorker();
|
||||
void doWriteWorker();
|
||||
int enterRT();
|
||||
int grblRTexecute(int ecmcError);
|
||||
void addCommand(std::string command);
|
||||
|
||||
void doReadWorker();
|
||||
void doMainWorker();
|
||||
void doWriteWorker();
|
||||
int enterRT();
|
||||
int grblRTexecute(int ecmcError);
|
||||
void addCommand(std::string command);
|
||||
int setExecute(int exe);
|
||||
int setHalt(int halt);
|
||||
int setResume(int resume);
|
||||
int setReset(int reset);
|
||||
private:
|
||||
void parseConfigStr(char *configStr);
|
||||
void autoEnableAtStart();
|
||||
bool getEcmcAxisEnabled(int axis_id);
|
||||
bool getAllConfiguredAxisEnabled();
|
||||
double getEcmcAxisActPos(int axis);
|
||||
void syncPositionIfNotEnabled();
|
||||
static std::string to_string(int value);
|
||||
int cfgDbgMode_;
|
||||
int cfgXAxisId_;
|
||||
int cfgYAxisId_;
|
||||
int cfgZAxisId_;
|
||||
int cfgSpindleAxisId_;
|
||||
int cfgAutoEnableAtStart_;
|
||||
int destructs_;
|
||||
int connected_;
|
||||
int errorCode_;
|
||||
double exeSampleTimeMs_;
|
||||
int grblInitDone_;
|
||||
void parseConfigStr(char *configStr);
|
||||
void preExeAxes();
|
||||
void postExeAxes();
|
||||
void preExeAxis(int ecmcAxisId, int grblAxisId);
|
||||
void postExeAxis(int ecmcAxisId, int grblAxisId);
|
||||
void autoEnableAxisAtStart(int ecmcAxisId);
|
||||
bool getEcmcAxisEnabled(int ecmcAxisId);
|
||||
bool getAllConfiguredAxisEnabled();
|
||||
double getEcmcAxisActPos(int axis);
|
||||
void syncAxisPositionIfNotEnabled(int ecmcAxisId, int grblAxisId);
|
||||
static std::string to_string(int value);
|
||||
int cfgDbgMode_;
|
||||
int cfgXAxisId_;
|
||||
int cfgYAxisId_;
|
||||
int cfgZAxisId_;
|
||||
int cfgSpindleAxisId_;
|
||||
int cfgAutoEnableAtStart_;
|
||||
int cfgAutoStart_;
|
||||
int destructs_;
|
||||
int executeCmd_;
|
||||
int resetCmd_;
|
||||
int haltCmd_;
|
||||
int resumeCmd_;
|
||||
int errorCode_;
|
||||
int ecmcError_;
|
||||
int errorCodeOld_;
|
||||
double exeSampleTimeMs_;
|
||||
int grblInitDone_;
|
||||
std::vector<std::string> grblCommandBuffer_;
|
||||
int grblCommandBufferIndex_;
|
||||
epicsMutexId grblCommandBufferMutex_;
|
||||
bool firstCommandWritten_;
|
||||
int autoEnableExecuted_;
|
||||
int grblExeCycles_;
|
||||
double timeToNextExeMs_;
|
||||
unsigned int grblCommandBufferIndex_;
|
||||
epicsMutexId grblCommandBufferMutex_;
|
||||
bool firstCommandWritten_;
|
||||
int autoEnableExecuted_;
|
||||
int grblExeCycles_;
|
||||
double timeToNextExeMs_;
|
||||
};
|
||||
|
||||
#endif /* ECMC_GRBL_H_ */
|
||||
|
||||
@@ -20,11 +20,13 @@
|
||||
#define ECMC_PLUGIN_Z_AXIS_ID_OPTION_CMD "Z_AXIS="
|
||||
#define ECMC_PLUGIN_SPINDLE_AXIS_ID_OPTION_CMD "SPINDLE_AXIS="
|
||||
#define ECMC_PLUGIN_AUTO_ENABLE_AT_START_OPTION_CMD "AUTO_ENABLE="
|
||||
#define ECMC_PLUGIN_AUTO_START_OPTION_CMD "AUTO_START="
|
||||
|
||||
#define ECMC_PLUGIN_ASYN_PREFIX "plugin.grbl"
|
||||
|
||||
#define ECMC_PLUGIN_GRBL_GENERAL_ERROR_CODE 0x100
|
||||
#define ECMC_PLUGIN_GRBL_COMMAND_ERROR_CODE 0x101
|
||||
#define ECMC_PLUGIN_AXIS_AT_LIMIT_ERROR_CODE 0x102
|
||||
#define ECMC_PLUGIN_GRBL_GRBL_STARTUP_STRING "for help]"
|
||||
#define ECMC_PLUGIN_GRBL_GRBL_OK_STRING "ok"
|
||||
#define ECMC_PLUGIN_GRBL_GRBL_ERR_STRING "error"
|
||||
|
||||
@@ -71,6 +71,34 @@ int realtime(int ecmcError) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int setExecute(int exe) {
|
||||
if(grbl){
|
||||
return grbl->setExecute(exe);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int setHalt(int halt) {
|
||||
if(grbl){
|
||||
return grbl->setHalt(halt);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int setResume(int resume) {
|
||||
if(grbl){
|
||||
return grbl->setResume(resume);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int setReset(int reset) {
|
||||
if(grbl){
|
||||
return grbl->setReset(reset);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void deleteGrbl() {
|
||||
if(grbl) {
|
||||
delete (grbl);
|
||||
|
||||
@@ -34,10 +34,26 @@ int createGrbl(char *configStr, int exeSampleTimeMs);
|
||||
*/
|
||||
int enterRT();
|
||||
|
||||
/** \brief execute from rt loop\n
|
||||
/** \brief rt loop\n
|
||||
*/
|
||||
int realtime(int ecmcError);
|
||||
|
||||
/** \brief execute g-code\n
|
||||
*/
|
||||
int setExecute(int exe);
|
||||
|
||||
/** \brief halt motion\n
|
||||
*/
|
||||
int setHalt(int halt);
|
||||
|
||||
/** \brief resume grbl\n
|
||||
*/
|
||||
int setResume(int resume);
|
||||
|
||||
/** \brief reset grbl\n
|
||||
*/
|
||||
int setReset(int reset);
|
||||
|
||||
// Delete object
|
||||
void deleteGrbl();
|
||||
|
||||
|
||||
@@ -98,9 +98,25 @@ int grblEnterRT(){
|
||||
int grblExitRT(void){
|
||||
return 0;
|
||||
}
|
||||
// Plc function for connect to can
|
||||
double grbl_connect() {
|
||||
return 0;
|
||||
|
||||
// Plc function for execute grbl code
|
||||
double grbl_set_execute(double exe) {
|
||||
return setExecute((int)exe);
|
||||
}
|
||||
|
||||
// Plc function for halt grbl
|
||||
double grbl_mc_halt(double halt) {
|
||||
return setHalt((int)halt);
|
||||
}
|
||||
|
||||
// Plc function for resume grbl
|
||||
double grbl_mc_resume(double halt) {
|
||||
return setResume((int)halt);
|
||||
}
|
||||
|
||||
// Plc function for reset grbl
|
||||
double grbl_mc_reset(double halt) {
|
||||
return setReset((int)halt);
|
||||
}
|
||||
|
||||
// Register data for plugin so ecmc know what to use
|
||||
@@ -117,7 +133,8 @@ struct ecmcPluginData pluginDataDef = {
|
||||
" "ECMC_PLUGIN_Y_AXIS_ID_OPTION_CMD"<axis id>: Ecmc Axis id for use as grbl Y axis, default = disabled (=-1).\n"
|
||||
" "ECMC_PLUGIN_Z_AXIS_ID_OPTION_CMD"<axis id>: Ecmc Axis id for use as grbl Z axis, default = disabled (=-1).\n"
|
||||
" "ECMC_PLUGIN_SPINDLE_AXIS_ID_OPTION_CMD"<axis id>: Ecmc Axis id for use as grbl spindle axis, default = disabled (=-1).\n"
|
||||
" "ECMC_PLUGIN_AUTO_ENABLE_AT_START_OPTION_CMD"<1/0>: Auto enable the linked ecmc axes autmatically before start, default = disabled (=0).\n"
|
||||
" "ECMC_PLUGIN_AUTO_ENABLE_AT_START_OPTION_CMD"<1/0>: Auto enable the linked ecmc axes autmatically before start, default = disabled (=0).\n"
|
||||
" "ECMC_PLUGIN_AUTO_START_OPTION_CMD"<1/0>: Auto start g-code at ecmc start, default = disabled (=0).\n"
|
||||
,
|
||||
// Plugin version
|
||||
.version = ECMC_EXAMPLE_PLUGIN_VERSION,
|
||||
@@ -133,17 +150,17 @@ struct ecmcPluginData pluginDataDef = {
|
||||
.realtimeExitFnc = grblExitRT,
|
||||
// PLC funcs
|
||||
.funcs[0] =
|
||||
{ /*----can_connect----*/
|
||||
{ /*----grbl_set_execute----*/
|
||||
// Function name (this is the name you use in ecmc plc-code)
|
||||
.funcName = "grbl_connect",
|
||||
.funcName = "grbl_set_execute",
|
||||
// Function description
|
||||
.funcDesc = "double grbl_connect() : Connect to grbl interface (from config str).",
|
||||
.funcDesc = "double grbl_set_execute(<exe>) : Trigg execution of loaded g-code at positive edge of <exe>",
|
||||
/**
|
||||
* 7 different prototypes allowed (only doubles since reg in plc).
|
||||
* Only funcArg${argCount} func shall be assigned the rest set to NULL.
|
||||
**/
|
||||
.funcArg0 = grbl_connect,
|
||||
.funcArg1 = NULL,
|
||||
.funcArg0 = NULL,
|
||||
.funcArg1 = grbl_set_execute,
|
||||
.funcArg2 = NULL,
|
||||
.funcArg3 = NULL,
|
||||
.funcArg4 = NULL,
|
||||
@@ -155,7 +172,76 @@ struct ecmcPluginData pluginDataDef = {
|
||||
.funcArg10 = NULL,
|
||||
.funcGenericObj = NULL,
|
||||
},
|
||||
.funcs[1] = {0}, // last element set all to zero..
|
||||
.funcs[1] =
|
||||
{ /*----can_connect----*/
|
||||
// Function name (this is the name you use in ecmc plc-code)
|
||||
.funcName = "grbl_mc_halt",
|
||||
// Function description
|
||||
.funcDesc = "double grbl_mc_halt(<halt>) : Halt grbl motion at positive edge of <halt>",
|
||||
/**
|
||||
* 7 different prototypes allowed (only doubles since reg in plc).
|
||||
* Only funcArg${argCount} func shall be assigned the rest set to NULL.
|
||||
**/
|
||||
.funcArg0 = NULL,
|
||||
.funcArg1 = grbl_mc_halt,
|
||||
.funcArg2 = NULL,
|
||||
.funcArg3 = NULL,
|
||||
.funcArg4 = NULL,
|
||||
.funcArg5 = NULL,
|
||||
.funcArg6 = NULL,
|
||||
.funcArg7 = NULL,
|
||||
.funcArg8 = NULL,
|
||||
.funcArg9 = NULL,
|
||||
.funcArg10 = NULL,
|
||||
.funcGenericObj = NULL,
|
||||
},
|
||||
.funcs[2] =
|
||||
{ /*----grbl_mc_resume----*/
|
||||
// Function name (this is the name you use in ecmc plc-code)
|
||||
.funcName = "grbl_mc_resume",
|
||||
// Function description
|
||||
.funcDesc = "double grbl_mc_resume(<resume>) : Resume halted grbl motion at positive edge of <resume>",
|
||||
/**
|
||||
* 7 different prototypes allowed (only doubles since reg in plc).
|
||||
* Only funcArg${argCount} func shall be assigned the rest set to NULL.
|
||||
**/
|
||||
.funcArg0 = NULL,
|
||||
.funcArg1 = grbl_mc_resume,
|
||||
.funcArg2 = NULL,
|
||||
.funcArg3 = NULL,
|
||||
.funcArg4 = NULL,
|
||||
.funcArg5 = NULL,
|
||||
.funcArg6 = NULL,
|
||||
.funcArg7 = NULL,
|
||||
.funcArg8 = NULL,
|
||||
.funcArg9 = NULL,
|
||||
.funcArg10 = NULL,
|
||||
.funcGenericObj = NULL,
|
||||
},
|
||||
.funcs[3] =
|
||||
{ /*----can_connect----*/
|
||||
// Function name (this is the name you use in ecmc plc-code)
|
||||
.funcName = "grbl_mc_reset",
|
||||
// Function description
|
||||
.funcDesc = "double grbl_mc_reset(<reset>) : Reset grbl at positive edge of <reset>",
|
||||
/**
|
||||
* 7 different prototypes allowed (only doubles since reg in plc).
|
||||
* Only funcArg${argCount} func shall be assigned the rest set to NULL.
|
||||
**/
|
||||
.funcArg0 = NULL,
|
||||
.funcArg1 = grbl_mc_reset,
|
||||
.funcArg2 = NULL,
|
||||
.funcArg3 = NULL,
|
||||
.funcArg4 = NULL,
|
||||
.funcArg5 = NULL,
|
||||
.funcArg6 = NULL,
|
||||
.funcArg7 = NULL,
|
||||
.funcArg8 = NULL,
|
||||
.funcArg9 = NULL,
|
||||
.funcArg10 = NULL,
|
||||
.funcGenericObj = NULL,
|
||||
},
|
||||
.funcs[4] = {0}, // last element set all to zero..
|
||||
// PLC consts
|
||||
.consts[0] = {0}, // last element set all to zero..
|
||||
};
|
||||
|
||||
@@ -56,7 +56,7 @@ void gc_init()
|
||||
// limit pull-off routines.
|
||||
void gc_sync_position()
|
||||
{
|
||||
PRINTF_DEBUG("");
|
||||
//PRINTF_DEBUG("");
|
||||
system_convert_array_steps_to_mpos(gc_state.position,sys_position);
|
||||
}
|
||||
|
||||
|
||||
@@ -59,7 +59,7 @@ epicsEnvSet("PLUGIN_VER" ,"develop")
|
||||
require ecmc_plugin_grbl $(PLUGIN_VER)
|
||||
|
||||
epicsEnvSet(ECMC_PLUGIN_FILNAME,"/home/pi/epics/base-7.0.5/require/${E3_REQUIRE_VERSION}/siteMods/ecmc_plugin_grbl/$(PLUGIN_VER)/lib/${EPICS_HOST_ARCH=linux-x86_64}/libecmc_plugin_grbl.so")
|
||||
epicsEnvSet(ECMC_PLUGIN_CONFIG,"DBG_PRINT=0;X_AXIS=1;Y_AXIS=2;AUTO_ENABLE=1;") # Only one option implemented in this plugin
|
||||
epicsEnvSet(ECMC_PLUGIN_CONFIG,"DBG_PRINT=1;X_AXIS=1;Y_AXIS=2;AUTO_ENABLE=1;AUTO_START=1;") # Only one option implemented in this plugin
|
||||
${SCRIPTEXEC} ${ecmccfg_DIR}loadPlugin.cmd, "PLUGIN_ID=0,FILE=${ECMC_PLUGIN_FILNAME},CONFIG='${ECMC_PLUGIN_CONFIG}', REPORT=1"
|
||||
epicsEnvUnset(ECMC_PLUGIN_FILNAME)
|
||||
epicsEnvUnset(ECMC_PLUGIN_CONFIG)
|
||||
@@ -68,32 +68,14 @@ epicsEnvUnset(ECMC_PLUGIN_CONFIG)
|
||||
ecmcGrblAddCommand("G1X20Y20F180");
|
||||
ecmcGrblAddCommand("G2X0Y0R20");
|
||||
ecmcGrblAddCommand("G0X10Y10");
|
||||
#ecmcGrblAddCommand("G2X0adadsdY0R20");
|
||||
ecmcGrblAddCommand("G1X0Y20");
|
||||
ecmcGrblAddCommand("G1X10Y0F360");
|
||||
ecmcGrblAddCommand("G4P1");
|
||||
ecmcGrblAddCommand("G1X50Y50F180");
|
||||
ecmcGrblAddCommand("G4P1");
|
||||
ecmcGrblAddCommand("G1X0Y0F360");
|
||||
ecmcGrblAddCommand("G1X20Y20F180");
|
||||
ecmcGrblAddCommand("G2X0Y0R20");
|
||||
ecmcGrblAddCommand("G0X10Y10");
|
||||
ecmcGrblAddCommand("G1X0Y20");
|
||||
ecmcGrblAddCommand("G1X10Y0F360");
|
||||
ecmcGrblAddCommand("G4P1");
|
||||
ecmcGrblAddCommand("G1X50Y50F180");
|
||||
ecmcGrblAddCommand("G4P1");
|
||||
ecmcGrblAddCommand("G1X0Y0F360");
|
||||
ecmcGrblAddCommand("G1X20Y20F180");
|
||||
ecmcGrblAddCommand("G2X0Y0R20");
|
||||
ecmcGrblAddCommand("G0X10Y10");
|
||||
ecmcGrblAddCommand("G1X0Y20");
|
||||
ecmcGrblAddCommand("G1X10Y0F360");
|
||||
ecmcGrblAddCommand("G4P1");
|
||||
ecmcGrblAddCommand("G1X50Y50F180");
|
||||
ecmcGrblAddCommand("G4P1");
|
||||
ecmcGrblAddCommand("G1X0Y0F360");
|
||||
ecmcGrblAddCommand("G2X0adadsdY0R20");
|
||||
ecmcGrblAddCommand("G1X0Y0");
|
||||
|
||||
#ecmcGrblAddCommand("G1X0Y20");
|
||||
#ecmcGrblAddCommand("G1X10Y0F360");
|
||||
#ecmcGrblAddCommand("G4P1");
|
||||
#ecmcGrblAddCommand("G1X50Y50F180");
|
||||
#ecmcGrblAddCommand("G1X0Y0");
|
||||
|
||||
##############################################################################
|
||||
## PLC 0
|
||||
@@ -114,7 +96,7 @@ $(SCRIPTEXEC) ($(ecmccfg_DIR)setAppMode.cmd)
|
||||
#asynSetTraceMask(MC_CPU1, -1, 0x41)
|
||||
# Note need to test 0x21 later..
|
||||
#asynSetTraceMask(MC_CPU1, -1, 0x21)
|
||||
asynSetTraceMask(MC_CPU1, -1, 0x41)
|
||||
asynSetTraceMask(MC_CPU1, -1, 0x0)
|
||||
iocInit()
|
||||
|
||||
dbpf $(IOC):Axis1.SPAM 0
|
||||
|
||||
Reference in New Issue
Block a user