LAPTOP-SNT8I5JK\Boounion
2025-06-19 d7973a57409adb886b1a7d1c71555b6fb54bae6c
1.启动自动搬送时,先发送start到各机台
已修改8个文件
181 ■■■■■ 文件已修改
SourceCode/Bond/Servo/CEFEM.cpp 19 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CEquipment.cpp 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CEquipment.h 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CMaster.cpp 117 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CMaster.h 10 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/Common.h 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/ServoCommo.h 5 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/ServoDlg.cpp 24 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
SourceCode/Bond/Servo/CEFEM.cpp
@@ -611,7 +611,7 @@
            CEqReadStep* pStep = new CEqReadStep(0x6301, 108 * 2,
                [&](void* pFrom, int code, const char* pszData, size_t size) -> int {
                    if (code == ROK && pszData != nullptr && size > 0) {
                        decodePanelDataReport((CStep*)pFrom, pszData, size);
                        decodeFacDataReport((CStep*)pFrom, pszData, size);
                    }
                    return -1;
                });
@@ -622,6 +622,23 @@
                delete pStep;
            }
        }
        {
            // Panel Data Request xxx
            CEqReadStep* pStep = new CEqReadStep(0x6301, 108 * 2,
                [&](void* pFrom, int code, const char* pszData, size_t size) -> int {
                    if (code == ROK && pszData != nullptr && size > 0) {
                        decodeFacDataReport((CStep*)pFrom, pszData, size);
                    }
                    return -1;
                });
            pStep->setName(STEP_EQ_FAC_DATA_REPORT);
            pStep->setProp("Port", (void*)1);
            pStep->setWriteSignalDev(0x04d);
            if (addStep(STEP_ID_PANEL_DATA_REQUEST, pStep) != 0) {
                delete pStep;
            }
        }
    }
    // 必须要实现的虚函数,在此初始化Slot信息
SourceCode/Bond/Servo/CEquipment.cpp
@@ -1021,7 +1021,7 @@
        unsigned short operationMode = (unsigned short)((unsigned short)mode + getIndexerOperationModeBaseValue());
        LOGI("<CEquipment-%s>准备设置indexerOperationMode<%d>", m_strName.c_str(), (int)mode);
        pStep->writeShort(operationMode, [&, mode](int code) -> int {
        pStep->writeShort(operationMode, [&, mode, onWritedRetBlock](int code) -> int {
            int retCode = 0;
            if (code == WOK) {
                LOGI("<CEquipment-%s>设置indexerOperationMode成功.", m_strName.c_str());
SourceCode/Bond/Servo/CEquipment.h
@@ -43,7 +43,7 @@
#define SIGNAL_UPSTREAM_TROUBLE    1
#define SIGNAL_INTERLOCK        2
#define SIGNAL_SEND_ABLE        3
    typedef std::function<int(int writeCode, int retCode)> ONWRITEDRET;
    typedef std::function<void(int writeCode, int retCode)> ONWRITEDRET;
    typedef std::function<void(void* pEiuipment, BOOL bAlive)> ONALIVE;
    typedef std::function<void(void* pEiuipment, int code)> ONDATACHANGED;
SourceCode/Bond/Servo/CMaster.cpp
@@ -1,6 +1,8 @@
#include "stdafx.h"
#include "Common.h"
#include "CMaster.h"
#include <future>
#include <vector>
namespace SERVO {
@@ -48,6 +50,7 @@
        m_ullRunTime = 0;
        m_state = MASTERSTATE::READY;
        m_pActiveRobotTask = nullptr;
        m_nLastError = 0;
        InitializeCriticalSection(&m_criticalSection);
    }
@@ -264,6 +267,13 @@
        return 0;
    }
    void CMaster::clearError()
    {
        m_nLastError = 0;
        m_strLastError = "";
        setState(MASTERSTATE::READY);
    }
    ULONGLONG CMaster::getRunTime()
    {
        if (m_state == MASTERSTATE::RUNNING)
@@ -325,8 +335,113 @@
            // 如果状态为STARTING,开始工作并切换到RUNNING状态
            lock();
            if (m_state == MASTERSTATE::STARTING) {
                // 发送indexerOperationModeChange到各个机台,成功后切换到RUNNING状态
                // 否则切换到MSERROR状态
                int nRet;
                CEquipment* pEq[6] = { pEFEM, pBonder1, pBonder2, pBakeCooling,
                    pVacuumBake, pMeasurement};
                BOOL bIomcOk[7] = {FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE};
                std::vector<std::promise<void>> promises(6);
                std::vector<std::future<void>> futures;
                nRet = pEq[0]->indexerOperationModeChange(IDNEXER_OPERATION_MODE::Start,
                    [&](int writeCode, int retCode) -> void {
                        bIomcOk[0] = retCode == (int)RET::OK;
                        promises[0].set_value();
                        TRACE("a0001\n", writeCode, retCode);
                    });
                if (nRet != 0) {
                    LOGI("<Master>EFEM切换Start状态失败");
                    m_strLastError = "EFEM切换Start状态失败.";
                    goto WAIT;
                }
                futures.push_back(promises[0].get_future());
                nRet = pEq[1]->indexerOperationModeChange(IDNEXER_OPERATION_MODE::Start,
                    [&](int writeCode, int retCode) -> void {
                        bIomcOk[1] = retCode == (int)RET::OK;
                        promises[1].set_value();
                        TRACE("a0002\n");
                    });
                if (nRet != 0) {
                    LOGI("<Master>Bonder1切换Start状态失败");
                    m_strLastError = "Bonder1切换Start状态失败.";
                    goto WAIT;
                }
                futures.push_back(promises[1].get_future());
                nRet = pEq[2]->indexerOperationModeChange(IDNEXER_OPERATION_MODE::Start,
                    [&](int writeCode, int retCode) -> void {
                        bIomcOk[2] = retCode == (int)RET::OK;
                        promises[2].set_value();
                        TRACE("a0003\n");
                    });
                if (nRet != 0) {
                    LOGI("<Master>Bonder2切换Start状态失败");
                    m_strLastError = "Bonder2切换Start状态失败.";
                    goto WAIT;
                }
                futures.push_back(promises[2].get_future());
                nRet = pEq[3]->indexerOperationModeChange(IDNEXER_OPERATION_MODE::Start,
                    [&](int writeCode, int retCode) -> void {
                        bIomcOk[3] = retCode == (int)RET::OK;
                        promises[3].set_value();
                        TRACE("a0004\n");
                    });
                if (nRet != 0) {
                    LOGI("<Master>BakeCooling切换Start状态失败");
                    m_strLastError = "BakeCooling切换Start状态失败.";
                    goto WAIT;
                }
                futures.push_back(promises[3].get_future());
                nRet = pEq[4]->indexerOperationModeChange(IDNEXER_OPERATION_MODE::Start,
                    [&](int writeCode, int retCode) -> void {
                        bIomcOk[4] = retCode == (int)RET::OK;
                        promises[4].set_value();
                        TRACE("a0005\n");
                    });
                if (nRet != 0) {
                    LOGI("<Master>VacuumBake切换Start状态失败");
                    m_strLastError = "VacuumBake切换Start状态失败.";
                    goto WAIT;
                }
                futures.push_back(promises[4].get_future());
                nRet = pEq[5]->indexerOperationModeChange(IDNEXER_OPERATION_MODE::Start,
                    [&](int writeCode, int retCode) -> void {
                        bIomcOk[5] = retCode == (int)RET::OK;
                        promises[5].set_value();
                        TRACE("a0006\n");
                    });
                if (nRet != 0) {
                    LOGI("<Master>Measurement切换Start状态失败");
                    m_strLastError = "Measurement切换Start状态失败.";
                    goto WAIT;
                }
                futures.push_back(promises[5].get_future());
WAIT:
                for (auto& f : futures) {
                    f.wait();  // 阻塞等待对应设备完成
                }
                for (int i = 0; i < 6; i++) {
                    if (!bIomcOk[i]) {
                        bIomcOk[6] = FALSE;
                        LOGI("<Master>%s切换Start状态失败", pEq[i]->getName().c_str());
                    }
                }
                // 检查看是否都已经切换到START状态
                if (!bIomcOk[6]) {
                unlock();
                Sleep(1000);
                    setState(MASTERSTATE::MSERROR);
                    continue;
                }
                unlock();
                setState(MASTERSTATE::RUNNING);
                continue;
            }
SourceCode/Bond/Servo/CMaster.h
@@ -16,11 +16,12 @@
namespace SERVO {
    enum MASTERSTATE {
    enum class MASTERSTATE {
        READY = 0,
        STARTING,
        RUNNING,
        STOPPING
        STOPPING,
        MSERROR
    };
    typedef std::function<void(void* pMaster, MASTERSTATE state)> ONMASTERSTATECHANGED;
@@ -55,6 +56,7 @@
        int term();
        int start();
        int stop();
        void clearError();
        ULONGLONG getRunTime();
        MASTERSTATE getState();
        unsigned DispatchProc();
@@ -122,6 +124,10 @@
        // 当前任务和已完成任务列表
        CRobotTask* m_pActiveRobotTask;
        std::list< CRobotTask* > m_listTask;
        // 错误代码
        int m_nLastError;
        std::string m_strLastError;
    };
}
SourceCode/Bond/Servo/Common.h
@@ -41,6 +41,7 @@
#define CR_MSGBOX_MESSAGE                    RGB(200, 216, 246)
#define TOP_TOOLBAR_BACKGROUND                RGB(240, 240, 240)    
#define STATUSBAR_BK_NORMAL                    RGB(195, 195, 195)
#define STATUSBAR_BK_STARTING                RGB(58, 127, 78)
#define STATUSBAR_BK_RUNNING                RGB(34, 177, 76)
#define STATUSBAR_BK_ALARM                    RGB(255, 127, 39)
@@ -318,6 +319,7 @@
#define STEP_ID_FETCHED_OUT_JOB_REPORT13        0x5BB
#define STEP_ID_FETCHED_OUT_JOB_REPORT14        0x5BC
#define STEP_ID_FETCHED_OUT_JOB_REPORT15        0x5BD
#define STEP_ID_PANEL_DATA_REQUEST                0x5D0
#define STEP_ID_PANEL_DATA_REPORT                0x5D1
#define STEP_ID_IN_OP_CMD_REPLY                    0x5F0
#define STEP_ID_DISPATCHING_MODE_CHANGE_REPLY    0x5F1
SourceCode/Bond/Servo/ServoCommo.h
@@ -9,6 +9,11 @@
#define SIGNAL_MAX                    8
#define ARM_ALL                        99
    enum class RET {
        OK = 1,
        NG,
    };
    enum class PortType {
        Loading = 1,
        Unloading,
SourceCode/Bond/Servo/ServoDlg.cpp
@@ -190,6 +190,18 @@
                    GetRuntimeFormatText(strText, "");
                    m_pMyStatusbar->setRunTimeText((LPTSTR)(LPCTSTR)strText);
                }
                else if (state == SERVO::MASTERSTATE::STARTING) {
                    m_pMyStatusbar->setBackgroundColor(STATUSBAR_BK_STARTING);
                    m_pMyStatusbar->setForegroundColor(RGB(0, 0, 0));
                    m_pMyStatusbar->setRunTimeText("正在启动...");
                }
                else if (state == SERVO::MASTERSTATE::MSERROR) {
                    m_pTopToolbar->GetBtn(IDC_BUTTON_RUN)->EnableWindow(TRUE);
                    m_pTopToolbar->GetBtn(IDC_BUTTON_STOP)->EnableWindow(FALSE);
                    m_pMyStatusbar->setBackgroundColor(STATUSBAR_BK_ALARM);
                    m_pMyStatusbar->setForegroundColor(RGB(0, 0, 0));
                    m_pMyStatusbar->setRunTimeText("启动失败.");
                }
                else if (state == SERVO::MASTERSTATE::RUNNING) {
                    m_pTopToolbar->GetBtn(IDC_BUTTON_RUN)->EnableWindow(FALSE);
                    m_pTopToolbar->GetBtn(IDC_BUTTON_STOP)->EnableWindow(TRUE);
@@ -856,14 +868,22 @@
{
    int id = (int)lParam;
    if (id == IDC_BUTTON_RUN) {
        theApp.m_model.getMaster().start();
        if (theApp.m_model.getMaster().getState() == SERVO::MASTERSTATE::MSERROR) {
            AfxMessageBox("当前有机台发生错误,不能启动,请确认解决问题后再尝试重新启动!");
        }
        else {
            if (theApp.m_model.getMaster().start() == 0) {
        m_pTopToolbar->GetBtn(IDC_BUTTON_RUN)->EnableWindow(FALSE);
    }
        }
    }
    else if (id == IDC_BUTTON_STOP) {
        theApp.m_model.getMaster().stop();
        if (theApp.m_model.getMaster().stop() == 0) {
        m_pTopToolbar->GetBtn(IDC_BUTTON_STOP)->EnableWindow(FALSE);
    }
    }
    else if (id == IDC_BUTTON_ROBOT) {
        theApp.m_model.getMaster().clearError();
        SERVO::CEFEM* pEFEM = (SERVO::CEFEM*)theApp.m_model.getMaster().getEquipment(EQ_ID_EFEM);
        CRobotCmdTestDlg dlg;
        dlg.SetEFEM(pEFEM);