123
This commit is contained in:
parent
fbc335082c
commit
38f3d606d0
|
@ -0,0 +1,20 @@
|
||||||
|
{
|
||||||
|
"version": "2.0.0",
|
||||||
|
"tasks": [
|
||||||
|
{
|
||||||
|
"label": "build C",
|
||||||
|
"type": "shell",
|
||||||
|
"command": "C:/msys64/mingw64/bin/gcc.exe",
|
||||||
|
"args": [
|
||||||
|
"${file}",
|
||||||
|
"-o",
|
||||||
|
"${fileDirname}/${fileBasenameNoExtension}.exe"
|
||||||
|
],
|
||||||
|
"group": {
|
||||||
|
"kind": "build",
|
||||||
|
"isDefault": true
|
||||||
|
},
|
||||||
|
"problemMatcher": ["$gcc"]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
|
@ -0,0 +1,16 @@
|
||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "windows-gcc-x64",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"C:/msys64/mingw64/include"
|
||||||
|
],
|
||||||
|
"compilerPath": "C:/msys64/mingw64/bin/gcc.exe",
|
||||||
|
"cStandard": "c11",
|
||||||
|
"cppStandard": "c++17",
|
||||||
|
"intelliSenseMode": "windows-gcc-x64"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
|
@ -0,0 +1,44 @@
|
||||||
|
{
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "C Launch",
|
||||||
|
"type": "cppdbg",
|
||||||
|
"request": "launch",
|
||||||
|
"program": "${fileDirname}/${fileBasenameNoExtension}.exe",
|
||||||
|
"args": [],
|
||||||
|
"stopAtEntry": false,
|
||||||
|
"cwd": "${fileDirname}",
|
||||||
|
"environment": [],
|
||||||
|
"externalConsole": true,
|
||||||
|
"MIMode": "gdb",
|
||||||
|
"miDebuggerPath": "C:/msys64/mingw64/bin/gdb.exe",
|
||||||
|
"setupCommands": [
|
||||||
|
{
|
||||||
|
"description": "Enable pretty-printing for gdb",
|
||||||
|
"text": "-enable-pretty-printing",
|
||||||
|
"ignoreFailures": true
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "C/C++ Runner: Debug Session",
|
||||||
|
"type": "cppdbg",
|
||||||
|
"request": "launch",
|
||||||
|
"args": [],
|
||||||
|
"stopAtEntry": false,
|
||||||
|
"externalConsole": true,
|
||||||
|
"cwd": "c:/Users/huiting/Desktop/py_document",
|
||||||
|
"program": "c:/Users/huiting/Desktop/py_document/build/Debug/outDebug",
|
||||||
|
"MIMode": "gdb",
|
||||||
|
"miDebuggerPath": "gdb",
|
||||||
|
"setupCommands": [
|
||||||
|
{
|
||||||
|
"description": "Enable pretty-printing for gdb",
|
||||||
|
"text": "-enable-pretty-printing",
|
||||||
|
"ignoreFailures": true
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
|
@ -0,0 +1,59 @@
|
||||||
|
{
|
||||||
|
"C_Cpp_Runner.cCompilerPath": "gcc",
|
||||||
|
"C_Cpp_Runner.cppCompilerPath": "g++",
|
||||||
|
"C_Cpp_Runner.debuggerPath": "gdb",
|
||||||
|
"C_Cpp_Runner.cStandard": "",
|
||||||
|
"C_Cpp_Runner.cppStandard": "",
|
||||||
|
"C_Cpp_Runner.msvcBatchPath": "C:/Program Files/Microsoft Visual Studio/VR_NR/Community/VC/Auxiliary/Build/vcvarsall.bat",
|
||||||
|
"C_Cpp_Runner.useMsvc": false,
|
||||||
|
"C_Cpp_Runner.warnings": [
|
||||||
|
"-Wall",
|
||||||
|
"-Wextra",
|
||||||
|
"-Wpedantic",
|
||||||
|
"-Wshadow",
|
||||||
|
"-Wformat=2",
|
||||||
|
"-Wcast-align",
|
||||||
|
"-Wconversion",
|
||||||
|
"-Wsign-conversion",
|
||||||
|
"-Wnull-dereference"
|
||||||
|
],
|
||||||
|
"C_Cpp_Runner.msvcWarnings": [
|
||||||
|
"/W4",
|
||||||
|
"/permissive-",
|
||||||
|
"/w14242",
|
||||||
|
"/w14287",
|
||||||
|
"/w14296",
|
||||||
|
"/w14311",
|
||||||
|
"/w14826",
|
||||||
|
"/w44062",
|
||||||
|
"/w44242",
|
||||||
|
"/w14905",
|
||||||
|
"/w14906",
|
||||||
|
"/w14263",
|
||||||
|
"/w44265",
|
||||||
|
"/w14928"
|
||||||
|
],
|
||||||
|
"C_Cpp_Runner.enableWarnings": true,
|
||||||
|
"C_Cpp_Runner.warningsAsError": false,
|
||||||
|
"C_Cpp_Runner.compilerArgs": [],
|
||||||
|
"C_Cpp_Runner.linkerArgs": [],
|
||||||
|
"C_Cpp_Runner.includePaths": [],
|
||||||
|
"C_Cpp_Runner.includeSearch": [
|
||||||
|
"*",
|
||||||
|
"**/*"
|
||||||
|
],
|
||||||
|
"C_Cpp_Runner.excludeSearch": [
|
||||||
|
"**/build",
|
||||||
|
"**/build/**",
|
||||||
|
"**/.*",
|
||||||
|
"**/.*/**",
|
||||||
|
"**/.vscode",
|
||||||
|
"**/.vscode/**"
|
||||||
|
],
|
||||||
|
"C_Cpp_Runner.useAddressSanitizer": false,
|
||||||
|
"C_Cpp_Runner.useUndefinedSanitizer": false,
|
||||||
|
"C_Cpp_Runner.useLeakSanitizer": false,
|
||||||
|
"C_Cpp_Runner.showCompilationTime": false,
|
||||||
|
"C_Cpp_Runner.useLinkTimeOptimization": false,
|
||||||
|
"C_Cpp_Runner.msvcSecureNoWarnings": false
|
||||||
|
}
|
|
@ -0,0 +1,50 @@
|
||||||
|
# pip install paho-mqtt
|
||||||
|
import json
|
||||||
|
import time
|
||||||
|
from paho.mqtt import client as mqtt
|
||||||
|
|
||||||
|
BROKER_HOST = "169.254.11.130"
|
||||||
|
BROKER_PORT = 1886
|
||||||
|
TOPIC = "topic_plc_and_py_for_AXIS"
|
||||||
|
|
||||||
|
# 建議測試用 QoS=1;retain=False
|
||||||
|
QOS = 1
|
||||||
|
RETAIN = False
|
||||||
|
|
||||||
|
def main():
|
||||||
|
client = mqtt.Client(client_id="py_pub_plc_test", protocol=mqtt.MQTTv311)
|
||||||
|
|
||||||
|
# 若 Broker 有帳密、TLS 在這裡設定(目前不需要)
|
||||||
|
# client.username_pw_set("user", "pass")
|
||||||
|
# client.tls_set(ca_certs="ca.pem") # 若是 TLS
|
||||||
|
|
||||||
|
client.connect(BROKER_HOST, BROKER_PORT, keepalive=60)
|
||||||
|
client.loop_start()
|
||||||
|
time.sleep(0.3) # 等連線建立
|
||||||
|
|
||||||
|
# ---- 第一組: ----
|
||||||
|
payload_forward = {
|
||||||
|
"Move_Forward": False, # BOOL
|
||||||
|
"Move_Forward_Velocity": 6.2 # REAL (float)
|
||||||
|
}
|
||||||
|
msg1 = json.dumps(payload_forward, ensure_ascii=False)
|
||||||
|
r1 = client.publish(TOPIC, msg1, qos=QOS, retain=RETAIN)
|
||||||
|
r1.wait_for_publish()
|
||||||
|
|
||||||
|
time.sleep(3)#第二顆馬達等等再開啟
|
||||||
|
|
||||||
|
# ---- 第二組: ----
|
||||||
|
payload_updown = {
|
||||||
|
"Move_UPDown": False, # BOOL
|
||||||
|
"Move_UPDown_Velocity": 5.1 # REAL (float)
|
||||||
|
}
|
||||||
|
msg2 = json.dumps(payload_updown, ensure_ascii=False)
|
||||||
|
r2 = client.publish(TOPIC, msg2, qos=QOS, retain=RETAIN)
|
||||||
|
r2.wait_for_publish()
|
||||||
|
|
||||||
|
time.sleep(0.3)
|
||||||
|
client.loop_stop()
|
||||||
|
client.disconnect()
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
main()
|
|
@ -0,0 +1,25 @@
|
||||||
|
import asyncio
|
||||||
|
from pymodbus.server import StartAsyncTcpServer
|
||||||
|
from pymodbus.datastore import ModbusSlaveContext, ModbusServerContext
|
||||||
|
from pymodbus.datastore.store import ModbusSequentialDataBlock
|
||||||
|
|
||||||
|
# 建立 HR 暫存區,從位址 1633 開始,總共 100 筆
|
||||||
|
store = ModbusSlaveContext(
|
||||||
|
hr=ModbusSequentialDataBlock(1633, [0]*100)
|
||||||
|
)
|
||||||
|
context = ModbusServerContext(slaves={255: store}, single=False)
|
||||||
|
|
||||||
|
async def read_loop():
|
||||||
|
while True:
|
||||||
|
# 從 HR address 1633 開始,讀取 3 筆資料
|
||||||
|
values = context[255].getValues(3, 1633, count=3)
|
||||||
|
print(f"PLC 寫入的資料: {values}")
|
||||||
|
await asyncio.sleep(1) # 每秒顯示一次
|
||||||
|
|
||||||
|
async def run_server():
|
||||||
|
asyncio.create_task(read_loop()) # 啟動背景讀取任務
|
||||||
|
await StartAsyncTcpServer(context, address=("169.254.11.130", 502))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
asyncio.run(run_server())
|
|
@ -0,0 +1,47 @@
|
||||||
|
import struct
|
||||||
|
import time
|
||||||
|
import threading
|
||||||
|
from pymodbus.client import ModbusTcpClient
|
||||||
|
from flask import Flask, jsonify
|
||||||
|
|
||||||
|
app = Flask(__name__)
|
||||||
|
|
||||||
|
modbus_data = {'rpm': 0, 'ai': 0, 'analog': 0} # 全域變數儲存資料
|
||||||
|
|
||||||
|
def read_modbus_data():
|
||||||
|
client = ModbusTcpClient(host="169.254.11.130", port=502)
|
||||||
|
if client.connect():
|
||||||
|
result = client.read_holding_registers(address=1633, count=6, slave=255)
|
||||||
|
client.close()
|
||||||
|
if result.isError():
|
||||||
|
return {'rpm': 'Error', 'ai': 'Error', 'analog': 'Error'}
|
||||||
|
else:
|
||||||
|
regs = result.registers
|
||||||
|
def to_float32(low, high):
|
||||||
|
return struct.unpack('<f', struct.pack('<HH', low, high))[0]
|
||||||
|
return {
|
||||||
|
'rpm': to_float32(regs[0], regs[1]),
|
||||||
|
'ai': to_float32(regs[2], regs[3]),
|
||||||
|
'analog': to_float32(regs[4], regs[5]),
|
||||||
|
}
|
||||||
|
else:
|
||||||
|
return {'rpm': 'Disconnected', 'ai': 'Disconnected', 'analog': 'Disconnected'}
|
||||||
|
|
||||||
|
def polling_loop():
|
||||||
|
global modbus_data
|
||||||
|
while True:
|
||||||
|
modbus_data = read_modbus_data()
|
||||||
|
print(modbus_data) # ✅ 持續印出
|
||||||
|
time.sleep(0.5)
|
||||||
|
|
||||||
|
@app.route("/")
|
||||||
|
def index():
|
||||||
|
return "✅ Flask is running. Visit /modbus to get data."
|
||||||
|
|
||||||
|
@app.route("/modbus")
|
||||||
|
def get_data():
|
||||||
|
return jsonify(modbus_data)
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
threading.Thread(target=polling_loop, daemon=True).start() # ✅ 背景輪詢
|
||||||
|
app.run(host='127.0.0.1', port=5000, debug=True)
|
|
@ -0,0 +1,11 @@
|
||||||
|
from pymodbus.client.sync import ModbusTcpClient
|
||||||
|
|
||||||
|
client = ModbusTcpClient(host="169.254.11.130", port=502) # 改為你的伺服器 IP
|
||||||
|
connection = client.connect()
|
||||||
|
|
||||||
|
if connection:
|
||||||
|
result = client.write_registers(address=1633, values=[123, 222, 789], unit=255)
|
||||||
|
print("✅ 寫入成功:", result)
|
||||||
|
client.close()
|
||||||
|
else:
|
||||||
|
print("❌ 無法連接到 Modbus 伺服器")
|
|
@ -0,0 +1,8 @@
|
||||||
|
from scapy.all import get_if_list, get_if_addr
|
||||||
|
|
||||||
|
for iface in get_if_list():
|
||||||
|
try:
|
||||||
|
ip = get_if_addr(iface)
|
||||||
|
print(f"{iface} → {ip}")
|
||||||
|
except Exception:
|
||||||
|
print(f"{iface} → 無法取得 IP")
|
|
@ -1,6 +1,6 @@
|
||||||
import cv2
|
import cv2
|
||||||
import mediapipe as mp
|
import mediapipe as mp
|
||||||
from pymodbus.client import ModbusTcpClient
|
from pymodbus.client.sync import ModbusTcpClient
|
||||||
|
|
||||||
# 初始化 Modbus TCP 客戶端
|
# 初始化 Modbus TCP 客戶端
|
||||||
client = ModbusTcpClient('169.254.11.8', port=502)
|
client = ModbusTcpClient('169.254.11.8', port=502)
|
||||||
|
@ -82,6 +82,4 @@ while True:
|
||||||
|
|
||||||
cap.release()
|
cap.release()
|
||||||
cv2.destroyAllWindows()
|
cv2.destroyAllWindows()
|
||||||
client.close()
|
client.close()
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,56 @@
|
||||||
|
from scapy.all import sniff, UDP, IP, get_if_list
|
||||||
|
import struct
|
||||||
|
|
||||||
|
# === 🧾 設定區 ===
|
||||||
|
TARGET_IP = "169.254.11.110" # 目標設備 IP
|
||||||
|
TARGET_PORT = 2312 # UDP 埠口
|
||||||
|
INTERFACE_NAME = r"\Device\NPF_{EA61A31B-056F-40E5-ADC8-5CEC3FEFDAE8}" # ✅ 換成你那張有 IP 的網卡
|
||||||
|
|
||||||
|
# === 📦 資料解析函數 ===
|
||||||
|
def analyze_payload(payload: bytes):
|
||||||
|
results = []
|
||||||
|
for i in range(0, len(payload), 8):
|
||||||
|
block = payload[i:i+8]
|
||||||
|
if len(block) < 8:
|
||||||
|
continue
|
||||||
|
try:
|
||||||
|
tag, type_code, value = struct.unpack('<H B x I', block)
|
||||||
|
results.append((f"0x{tag:04X}", type_code, value))
|
||||||
|
except struct.error:
|
||||||
|
continue
|
||||||
|
return results
|
||||||
|
|
||||||
|
# === 🖥️ 封包處理函數 ===
|
||||||
|
def handle_packet(pkt):
|
||||||
|
if UDP in pkt and IP in pkt:
|
||||||
|
ip_layer = pkt[IP]
|
||||||
|
udp_layer = pkt[UDP]
|
||||||
|
|
||||||
|
if ip_layer.src == TARGET_IP or ip_layer.dst == TARGET_IP:
|
||||||
|
print(f"\n📦 封包來自 {ip_layer.src} → {ip_layer.dst}")
|
||||||
|
payload = bytes(udp_layer.payload)
|
||||||
|
|
||||||
|
if len(payload) == 0:
|
||||||
|
print("⚠️ 無 payload,跳過")
|
||||||
|
return
|
||||||
|
|
||||||
|
result = analyze_payload(payload)
|
||||||
|
print(f"📊 分析結果,共 {len(result)} 筆:")
|
||||||
|
for tag, typ, val in result:
|
||||||
|
print(f" ➤ Tag: {tag} | Type: {typ} | Value: {val}")
|
||||||
|
|
||||||
|
# === ✅ 檢查介面是否存在 ===
|
||||||
|
if INTERFACE_NAME not in get_if_list():
|
||||||
|
print("❌ 找不到指定的網卡:", INTERFACE_NAME)
|
||||||
|
print("✅ 可選網卡如下:")
|
||||||
|
for iface in get_if_list():
|
||||||
|
print(" -", iface)
|
||||||
|
exit(1)
|
||||||
|
|
||||||
|
# === 🚀 開始監控 ===
|
||||||
|
print(f"📡 正在監控介面:{INTERFACE_NAME},目標 IP: {TARGET_IP}, Port: {TARGET_PORT}")
|
||||||
|
sniff(
|
||||||
|
iface=INTERFACE_NAME,
|
||||||
|
filter=f"udp and host {TARGET_IP} and port {TARGET_PORT}",
|
||||||
|
prn=handle_packet
|
||||||
|
)
|
|
@ -0,0 +1,47 @@
|
||||||
|
from flask import Flask, jsonify, render_template_string
|
||||||
|
|
||||||
|
html_page = """
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<title>Modbus 即時資料</title>
|
||||||
|
<style>
|
||||||
|
body { font-family: Arial, sans-serif; font-size: 20px; padding: 20px; }
|
||||||
|
.label { font-weight: bold; }
|
||||||
|
</style>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<h1>📊 Modbus 即時資料</h1>
|
||||||
|
<p><span class="label">RPM (地址1633):</span> <span id="rpm">載入中...</span></p>
|
||||||
|
<p><span class="label">AI 電壓 (地址1635):</span> <span id="ai">載入中...</span></p>
|
||||||
|
<p><span class="label">類比訊號值 (地址1637):</span> <span id="analog">載入中...</span></p>
|
||||||
|
|
||||||
|
|
||||||
|
<script>
|
||||||
|
async function fetchData() {
|
||||||
|
try {
|
||||||
|
const response = await fetch('/modbus'); // ✅ 修改這行
|
||||||
|
const result = await response.json();
|
||||||
|
|
||||||
|
document.getElementById('rpm').textContent = result.rpm;
|
||||||
|
document.getElementById('ai').textContent = result.ai;
|
||||||
|
document.getElementById('analog').textContent = result.analog;
|
||||||
|
} catch (error) {
|
||||||
|
document.getElementById('rpm').textContent = '錯誤';
|
||||||
|
document.getElementById('ai').textContent = '錯誤';
|
||||||
|
document.getElementById('analog').textContent = '錯誤';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
setInterval(fetchData, 1000);
|
||||||
|
fetchData();
|
||||||
|
</script>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
|
"""
|
||||||
|
|
||||||
|
@app.route("/")
|
||||||
|
def index():
|
||||||
|
return render_template_string(html_page)
|
|
@ -0,0 +1,31 @@
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
typedef struct point {
|
||||||
|
int x;
|
||||||
|
int y;
|
||||||
|
char *number;
|
||||||
|
struct point *ptr_for_go_next;
|
||||||
|
} point_t;
|
||||||
|
|
||||||
|
int main() {
|
||||||
|
point_t p2 = {
|
||||||
|
.x = 20,
|
||||||
|
.y = 40,
|
||||||
|
.number = "number_2",
|
||||||
|
.ptr_for_go_next = NULL
|
||||||
|
};
|
||||||
|
|
||||||
|
point_t p1 = {
|
||||||
|
.x = 10,
|
||||||
|
.y = 20,
|
||||||
|
.number = "number_1",
|
||||||
|
.ptr_for_go_next = &p2
|
||||||
|
};
|
||||||
|
|
||||||
|
printf("x: %d\n", p1.x);
|
||||||
|
printf("y: %d\n", p1.y);
|
||||||
|
printf("number: %s\n", p1.number);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
Loading…
Reference in New Issue