knowledge(경쟁사): 모듈 46개 export 전수 — 계산 공용 라이브러리·동글·8차 해소
11번은 핵심 CPM 12개만 다뤘고 32개 모듈이 손대지 않은 채였음. 플러그인 규약 - 46개 중 31개 모듈이 Calc_Kanjub 를 내보냄. 재계산 진입점이 한 곳이 아니라 모듈마다 있음. T8(UI 명령별 재계산 범위)이 어려운 까닭 DP_Common.CPM 73함수 = 계산 공용 라이브러리 - 식 평가 CALC_STR·CALC_STR_PART·CALC_STR_URC·GET_URC_TYP - 중간변수 GET_VARI_VAL·SET_VARI_VAL (:=A01 라벨) - 반올림 MROUNDUD·MROUNDUP·MTRUNC·MINT·MFRAC·GET_ROUND_CUT - 조건 IIF·IFI·IFO·CHK_TRUE_CLSTR — 식에 조건 분기가 들어감 - AMTTOHAN 금액 한글 변환 - ⇒ 식 평가기는 사칙연산+ROUND 만으로 부족. 조건 함수와 중간변수 필요 ST_P_XLS.CPM 72함수 — 엑셀이 양방향 교환 경로 - CONV_XLS_2_ST(엑셀→STmate 역등록)·XLS_2_BDREC(엑셀→BDQTY)·Prn_FMLA_INFO - 암호화된 BDQTY 를 엑셀에서 만들 수 있다는 뜻 SX32W.CPM 29함수 = Rainbow Sentinel SuperPro 동글 API - 라이선스가 소프트키가 아니라 USB 동글. 통제시험이 영구 불가인 근거 확정 ST_Jabpum: Edt_Hal_Amt / Edt_Hal_Rate — 할증이 금액·율 두 갈래 변경 차수 8차 의문 해소 - PRJLST.SMT 섹션 최대 2, DBF 접미사 1~4, 바이너리에 1~3차변경만, BOQ2* 없음. 한 파일은 4벌이 맞고 8차는 분리형 파일 선택임 문서 24 신규, export 원자료와 스크립트 2개 추가. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01Prk9BCHG1EMAywk9k8wegA
This commit is contained in:
@@ -30,6 +30,7 @@
|
||||
| 21 정정과 트랙 통합 | **⛔ `SMT` 판정 정정 · 지식DB 트랙 셋 통합 · `PRJLST.SMT` 설정 원장 · 암호화의 성격** | (저장소 파일) |
|
||||
| 22 UI 폼 분석 | **폼 233개 중 3개만 봤던 것** — 선택축 272개, `ACTTYP`·자리수 키·일괄변경 규칙 | (저장소 파일) |
|
||||
| 23 `COSTN.SMT` 전수파싱 | **단가산출 원장** — 참조 1,570·품 1,460·Q식 187개(10꼴)·운반 사이클 | (저장소 파일) |
|
||||
| 24 모듈구조 전수 | **46개 모듈 export** — `DP_Common` 73함수, 플러그인 규약, 동글, 8차 해소 | (저장소 파일) |
|
||||
|
||||
> **정본은 저장소 파일이다** — `resources/knowledge/original/경쟁사 프로그램/STmate 분석/20_분석/`.
|
||||
> 위 Orca 링크는 보기용이며, 문서를 지식DB 자리로 옮기면서 주소가 한 번 바뀌었다.
|
||||
@@ -90,7 +91,13 @@
|
||||
| `COSTN.SMT` 내용 | 「평문」까지만 | **전수 파싱** — 중기 참조 1,504건, 성분 셋을 각각 | 23번 |
|
||||
| `Q` 식 | 한 꼴로 알았음 | ⚠ **최소 10가지 꼴** — 하드코딩 금지 | 23번 §3 |
|
||||
| 운반 사이클 | 안 봤음 | **적재+왕복+적하** 구조·인자 확인 | 23번 §4 |
|
||||
| 할증률 | `BDQTY` 암호화로 막힘 | ◐ **적용값 92건은 읽힘** | 23번 §5 |
|
||||
| 할증률 | `BDQTY` 암호화로 막힘 | ◐ **적용값 92건은 읽힘**. 편집은 **금액·율 두 갈래** | 23번 §5, 24번 §5 |
|
||||
| 모듈 분석 | 핵심 12개 | **46개 전수 export** | 24번 |
|
||||
| 식 평가기 함수 | `CALC_STR` 만 | **A** — `DP_Common` 73함수. 조건 `IIF`·중간변수·`MFRAC` 포함 | 24번 §2 |
|
||||
| 재계산 진입점 | 한 곳으로 봄 | ⚠ **31개 모듈이 `Calc_Kanjub` 보유** | 24번 §1 |
|
||||
| 라이선스 | 「없음」 | **Rainbow Sentinel SuperPro 하드웨어 동글** | 24번 §4 |
|
||||
| 엑셀 | 단방향 출력 | **양방향** — `CONV_XLS_2_ST`·`XLS_2_BDREC` | 24번 §3 |
|
||||
| 변경 차수 8차 | ⚠ 미해결 | ✅ **해소** — 한 파일 4벌, 8차는 분리형 파일 선택 | 24번 §7 |
|
||||
|
||||
분석일: 2026-09-13
|
||||
대상: `C:\경영정보(주)`
|
||||
|
||||
@@ -0,0 +1,121 @@
|
||||
# 모듈 구조 전수 — 46개 모듈의 export 와 플러그인 규약
|
||||
|
||||
점검일: 2026-09-13
|
||||
계기: 11번은 **핵심 CPM 12개**만 다뤘다. 나머지 **32개 모듈**이 손대지 않은 채였다.
|
||||
재현 스크립트: `40_스크립트/module_export_sweep.py`
|
||||
|
||||
## 1. 플러그인 규약 — `Calc_Kanjub`
|
||||
|
||||
**46개 모듈 중 31개가 `Calc_Kanjub` 를 내보낸다.** 편집·인쇄·변환 무엇이든 **제비율 재계산을 스스로 부를 수 있는 공통 진입점**이다.
|
||||
|
||||
```text
|
||||
Calc_Kanjub 31개 모듈이 공유
|
||||
```
|
||||
|
||||
⇒ 「어느 화면에서 무엇을 고쳐도 제비율이 다시 돌 수 있다」는 뜻이다. 13번 **T8(UI 명령별 재계산 범위)**이 왜 어려운지가 여기서 보인다 — 재계산 진입점이 한 곳이 아니라 **모듈마다** 있다.
|
||||
|
||||
## 2. ⭐ `DP_Common.CPM` — 계산 공용 라이브러리 73함수
|
||||
|
||||
11번 §4.1은 `CALC_STR`만 언급했다. **실제 함수 집합 전체**는 이렇다.
|
||||
|
||||
### 2.1 식 평가
|
||||
|
||||
```text
|
||||
CALC_STR 식 문자열 평가
|
||||
CALC_STR_PART 부분 평가
|
||||
CALC_STR_URC URC(자원참조) 포함 평가 ← &M00034M& 계열을 푸는 자리
|
||||
GET_URC_TYP 참조 종류 판정
|
||||
GET_VARI_VAL 변수 읽기 SET_VARI_VAL 변수 쓰기 ← :=A01 중간라벨
|
||||
```
|
||||
|
||||
### 2.2 반올림·수치 — 11번 §4.2의 원 함수가 전부 여기 있다
|
||||
|
||||
```text
|
||||
MROUNDUD 반올림 계열 MROUNDUP 올림 MTRUNC 절사
|
||||
MINT 정수화 MFRAC 소수부
|
||||
GET_ROUND_CUT 설정에 따라 위를 고르는 디스패처
|
||||
MSTRTODBL · MSTRTOINT · ISNUM · ISINT · CH_FNTOVAL · FLOATTOSTR_ · EXTTOSTR
|
||||
```
|
||||
|
||||
⇒ **`MFRAC`(소수부)가 새로 나왔다.** 18번 §2.2의 「`Q`를 소수 2자리로 먼저 확정」·17번 §2의 「성분 소계 절사」처럼 **소수부를 따로 다루는 자리**가 실제로 함수로 있다.
|
||||
|
||||
### 2.3 조건·논리
|
||||
|
||||
```text
|
||||
IIF IFI IFO CHK_TRUE_CLSTR COUNT_LOGICAL
|
||||
```
|
||||
|
||||
⇒ 식 문자열에 **조건 분기**가 들어간다. 11번 §4.1의 「선택 토큰(`[+LAB]`·`[+ANJ_B]`)을 옵션에 따라 포함/제거」가 이 함수들로 처리된다.
|
||||
|
||||
### 2.4 문자열·기타
|
||||
|
||||
`ADDBJVAL` · `ADDBSL` · `ADDSPSTR` · `CHANGE_STR` · `COPY_LEFT/RIGHT` · `LEFT_STR` · `RIGHT_STR` · `SEP_STR` · `REPLICA_STR` · `COUNT_STR` · `MPOS` · `NPOS` · `BPOS` · `DIS_FMT` · **`AMTTOHAN`**(금액 한글 변환 — 「금 일억삼천사백이십만원정」) · 파일 조작 20여 개.
|
||||
|
||||
**재구현 지침** — 식 평가기는 `+ - * /` 와 `ROUND` 계열만으로 부족하다. **`IIF`·`IFI`·`IFO` 조건 함수와 `GET_VARI_VAL`/`SET_VARI_VAL` 중간변수**까지 갖춰야 한다.
|
||||
|
||||
## 3. `ST_P_XLS.CPM` — XLSX 입출력 72함수
|
||||
|
||||
| 함수 | 뜻 |
|
||||
|---|---|
|
||||
| `MAKE_XLS` · `SHOW_XLS` · `FREE_XLS` | 엑셀 생성·표시·해제 |
|
||||
| **`CONV_XLS_2_ST`** | **엑셀 → STmate 역등록** |
|
||||
| **`XLS_2_BDREC`** | 엑셀 → `BDQTY` 레코드 |
|
||||
| **`Prn_FMLA_INFO`** | **수식 정보 출력** — 출력 XLSX에 수식이 남는 까닭 |
|
||||
| `MK_BSCBOQ_EXL` · `MK_EXL_BSCBOQ` | 기준 BOQ 양방향 |
|
||||
| `Prn_*_EXL` 약 55개 | `SET_REP` 서식마다 엑셀판 |
|
||||
|
||||
⇒ **엑셀이 단순 출력이 아니라 양방향 교환 경로**다. `〓 INITIAL 〓` 시트(18번 §2.3)가 재등록 메타인 까닭이 `CONV_XLS_2_ST`에 있다.
|
||||
|
||||
⚠ **`XLS_2_BDREC`** — 암호화된 `BDQTY`를 **엑셀에서 만들 수 있다.** 뒤집으면 `BDQTY` 내용이 엑셀 수량산출 양식과 대응한다는 뜻이다.
|
||||
|
||||
## 4. `SX32W.CPM` — 라이선스는 하드웨어 동글
|
||||
|
||||
```text
|
||||
RNBOsproInitialize · RNBOsproFindFirstUnit · RNBOsproQuery · RNBOsproRead
|
||||
RNBOsproGetKeyInfo · RNBOsproGetSubLicense · RNBOsproSetDeveloperCode
|
||||
RNBOsproCheckTerminalService · RNBOsproSetHeartBeat · RNBOsproReleaseLicense …29개
|
||||
```
|
||||
|
||||
**Rainbow(현 Thales) Sentinel SuperPro** API다. `ST_BdSN.CPM`의 `Chk_BD_SN`·`Chk_REG_SN`(시리얼 검사)이 함께 있다.
|
||||
|
||||
⇒ **라이선스가 소프트 키가 아니라 USB 동글**이다. 13번의 통제시험 T1~T11이 왜 「영구 불가」인지가 확정됐다 — 동글이 없으면 실행 자체가 안 된다.
|
||||
|
||||
## 5. 그 밖에 드러난 모듈
|
||||
|
||||
| 모듈 | export | 뜻 |
|
||||
|---|---:|---|
|
||||
| `ST_U_Archive.CPM` | 16 | **STC 압축·해제** — `Chk_STC_Ver`(버전) · `ComP_Data` · `UnPack`/`UnPack1`/`UnPack_No` |
|
||||
| `ST_P_Excav.CPM` | 15 | **굴착 전용 내역 양식** — `Prn_Nae_Ex1_*` · `Ex2_*` 계열. 도로공사 양식 |
|
||||
| `ST_P_Nae.CPM` | 30 | 내역·원가 인쇄 본진 |
|
||||
| `ST_P_List.CPM` | 11 | 목록표 계열 |
|
||||
| **`ST_Jabpum.CPM`** | 6 | **`Edt_Hal_Amt` vs `Edt_Hal_Rate`** — 할증을 **금액과 율 두 갈래**로 편집. 07번 §4의 「수량 할증 ≠ 금액 가산」이 export 이름에 그대로 |
|
||||
| `ST_U_ADL.CPM` | 6 | 온라인 갱신 — `ST_Down_File` · `ST_UP_INFO_R` · `ST_SND_Mail` |
|
||||
| `ST_Com_V.CPM` | 10 | `GET_*_R` 계열 — 모듈 간 자원 조회 규약 |
|
||||
| `ST_Func_C.CPM` | 7 | `SUM_TOT` · `CON_TOT` · `ZERO_TOT` · `PCN_TO_T` · `OPTIMIZ` — **계층 합산** |
|
||||
| `CPMARC`/`CPMUNA` | 4+4 | ZIP 압축·해제 (Info-ZIP) |
|
||||
| `STmexe.Cpm` | 2 | `Chk_Exe` · `Chk_New_Exe` — 자기 갱신 |
|
||||
|
||||
## 6. 이번 점검이 바꾸는 것
|
||||
|
||||
| 항목 | 이전 | 지금 |
|
||||
|---|---|---|
|
||||
| 모듈 분석 범위 | 핵심 12개 | **46개 전수 export** |
|
||||
| 식 평가기 함수 집합 | `CALC_STR`만 알았음 | ✅ **73함수** — 조건(`IIF`)·중간변수·`MFRAC`까지 |
|
||||
| 재계산 진입점 | 한 곳으로 봄 | ⚠ **31개 모듈이 `Calc_Kanjub` 보유** — T8이 어려운 까닭 |
|
||||
| 라이선스 | 「없음」까지만 | ✅ **Rainbow Sentinel SuperPro 하드웨어 동글** |
|
||||
| 엑셀 | 단방향 출력으로 봄 | ✅ **양방향** — `CONV_XLS_2_ST` · `XLS_2_BDREC` |
|
||||
| 할증 | 한 갈래로 봄 | ✅ **금액·율 두 갈래** (`Edt_Hal_Amt`/`Edt_Hal_Rate`) |
|
||||
| 변경 차수 8차 의문 | 미해결 | ✅ **해소** — 아래 |
|
||||
|
||||
## 7. 변경 차수 8차 의문 해소
|
||||
|
||||
22번 §3.3에서 「화면은 8차인데 `COSTN` 접미사는 4벌」이라 남겨 둔 것을 확인했다.
|
||||
|
||||
| 근거 | 결과 |
|
||||
|---|---|
|
||||
| `PRJLST.SMT` 차수 섹션 | 표본 7건 모두 **최대 `[1_KANJUB]`·`[2_KANJUB]`** |
|
||||
| DBF 접미사 | `PRJLST`·`BOQ11`·`COSTN` 모두 **1~4 네 벌** |
|
||||
| 바이너리 문자열 | **`1차변경`~`3차변경`만** 존재. 4~8차 없음 |
|
||||
| `BOQ1*` / `BOQ2*` | `BOQ1` 15개 모듈, **`BOQ2`는 0개** |
|
||||
|
||||
⇒ **한 파일이 담는 것은 4벌(원설계 + 3차변경)이 맞다.** 화면의 1~8차는 **분리형으로 파일을 이어 갔을 때 그 파일들을 고르는 인쇄 선택**이다(16번 §4.6의 차수 인계). 저장 구조 의문은 없다.
|
||||
@@ -0,0 +1,61 @@
|
||||
### CPM/EXE export 전수 — 모듈 44개, export 408개(중복포함)
|
||||
11번이 다룬 핵심 12개 말고 **32개 모듈**이 남아 있었음
|
||||
|
||||
CPMARC.CPM 4개 GetZipDllPrivVersion, GetZipDllVersion, ZipDllExec, ___CPPdebugHook
|
||||
CPMUNA.CPM 4개 GetUnzDllPrivVersion, GetUnzDllVersion, UnzDllExec, ___CPPdebugHook
|
||||
DP_Common.CPM 73개 ADDBJVAL, ADDBSL, ADDSPSTR, AMTTOHAN, BPOS, CALC_STR, CALC_STR_PART, CALC_STR_URC, CHANGE_STR, C
|
||||
DP_MinMsg.CPM 3개 GETNEWCODE_NAME, GETSPCHAR, MINIMSG
|
||||
ST_BdSN.CPM 3개 Chk_BD_SN, Chk_BD_USE, Chk_REG_SN
|
||||
✅ ST_Boq.CPM 4개 Add_From_MRG, Calc_Kanjub, Edit_Boq, Edit_Bqm
|
||||
ST_Com_V.CPM 10개 GET_CAL_R, GET_COM_R, GET_IMS_R, GET_MRG_R, GET_PBL_R, GET_PRN_R, GET_SFC_R, GET_STM_R, GET_SYS_
|
||||
ST_EdSan.CPM 3개 Calc_Kanjub, Edit_EQ_SYNC, Edit_SanKun
|
||||
✅ ST_EdiLWi.CPM 2개 Calc_Kanjub, Edit_iLW
|
||||
ST_FindUse.CPM 3개 Calc_Kanjub, Find_BDQ, Find_BOQ
|
||||
ST_Func_C.CPM 7개 CON_TOT, OPTIMIZ, PCN_TO_T, SUM_TOT, VALTOPOS, ZERO_TO, ZERO_TOT
|
||||
ST_Jabpum.CPM 6개 Calc_Kanjub, Edit_Dan, Edit_Strg, Edt_Hal_Amt, Edt_Hal_Rate, View_JabPum
|
||||
✅ ST_KanJub.CPM 5개 Calc_Kanjub, Edit_KanJub, Edit_KanJub_K, Edit_Kan_Rate, Prn_Kan_Rate
|
||||
ST_Merge_Code.CPM 1개 Calc_Kanjub
|
||||
ST_PList.CPM 3개 Calc_Kanjub, Call_MRG, Call_PLIST
|
||||
✅ ST_P_Collect.CPM 5개 Calc_Kanjub, Prn_Col_Dan, Prn_Col_Dan_L, Prn_Col_X, Prn_Col_X_L
|
||||
✅ ST_P_ConEst.CPM 9개 Calc_Kanjub, Prn_Jab_K, Prn_Nae_C1, Prn_Nae_C2, Prn_Nae_C3, Prn_Nae_Est, Prn_Nae_K1, Prn_Nae_K2,
|
||||
ST_P_Excav.CPM 15개 Calc_Kanjub, Prn_Nae_Ex1_0, Prn_Nae_Ex1_1, Prn_Nae_Ex1_2, Prn_Nae_Ex1_C1, Prn_Nae_Ex1_C2, Prn_Na
|
||||
✅ ST_P_Joong.CPM 7개 Calc_Kanjub, Prn_Joong, Prn_Joong2, Prn_Joong2_L, Prn_Joong_C, Prn_Joong_C_L, Prn_Joong_L
|
||||
ST_P_List.CPM 11개 Calc_Kanjub, Prn_AList, Prn_Comp_M, Prn_Comp_M1, Prn_Comp_M1_L, Prn_Dan, Prn_Dan_L, Prn_SanMok,
|
||||
ST_P_Nae.CPM 30개 Calc_Kanjub, Prn_Boq_Not, Prn_Bqm, Prn_Jab, Prn_Jab_P, Prn_Nae, Prn_NaeW, Prn_NaeW_P, Prn_Nae_B,
|
||||
ST_P_San.CPM 3개 Calc_Kanjub, Prn_San_L, Prn_San_P
|
||||
ST_P_XLS.CPM 72개 CONV_XLS_2_ST, Calc_Kanjub, Chk_Xls_File, FIND_PRT_INDX, FREE_XLS, MAKE_XLS, MK_BSCBOQ_EXL, MK_E
|
||||
ST_P_iLWi.CPM 3개 Calc_Kanjub, Prn_iLWi, Prn_iLWi_S
|
||||
ST_Prt.CPM 4개 Calc_Kanjub, GS_Prn_Rec, Prn_Prt, Rep_Print
|
||||
✅ ST_SanCal.CPM 2개 Calc_Kanjub, Calq_San
|
||||
ST_Sys.CPM 2개 Calc_Kanjub, Set_Sys_1
|
||||
ST_U_ADL.CPM 6개 Get_Real_Time, ST_Down_File, ST_NEW_INFO, ST_SND_Mail, ST_UP_DNINFO, ST_UP_INFO_R
|
||||
ST_U_Archive.CPM 16개 Calc_Kanjub, Chk_ArcName, Chk_Data, Chk_STC_Ver, Chk_STDir, ComP_CurBOQ, ComP_Data, ComP_FOLD, C
|
||||
✅ ST_U_ChgAmt.CPM 2개 CHANGE_AMT, Calc_Kanjub
|
||||
✅ ST_U_ChgCode.CPM 10개 Calc_Kanjub, Chg_Code_All, Chg_Code_Plus, Chg_Code_Sel, Chk_Chg_Code_1, Chk_True_Rep_Code, Exec_
|
||||
✅ ST_U_ConBD.CPM 4개 CONBD_USD_QTY, CON_QTY, CON_QTY9, Calc_Kanjub
|
||||
✅ ST_U_Convert.CPM 20개 Appn_Tag_REP, CHK_K_FLD, Calc_Kanjub, Conv_BOQ, Conv_Equip, Conv_Jodal_ST8, Conv_ST8_Jodal, Conv
|
||||
ST_U_DelCode.CPM 6개 Calc_Kanjub, Chk_True_Del_1, Del_Code_A_T, Del_Code_A_X, Del_Code_Sel, Exec_Delete_Code
|
||||
ST_U_DelPrj.CPM 3개 Calc_Kanjub, Delete_Prj, Merge_Prj
|
||||
ST_U_Indx.CPM 2개 Calc_Kanjub, INDX_ALL
|
||||
ST_U_Merge.CPM 2개 Calc_Kanjub, ST_MERGE
|
||||
ST_VSetup.EXE 2개 _MainWndProc@16, _StubFileWrite@12
|
||||
STmate.Cpm 1개 Calc_Kanjub
|
||||
✅ STmateQty8.CPM 4개 Calc_Kanjub, FIND_QCODE, Free_Qty, ST_QTY
|
||||
STmexe.Cpm 2개 Chk_Exe, Chk_New_Exe
|
||||
SX32W.CPM 29개 RNBOsproActivate, RNBOsproCheckTerminalService, RNBOsproCleanup, RNBOsproDecrement, RNBOsproEnum
|
||||
UNWISE.EXE 4개 _ItemDlg@16, _MainWndProc@16, _PromptDlg@16, _SharedDlg@16
|
||||
View_Old_San.CPM 1개 Show_Old_San
|
||||
|
||||
### 여러 모듈이 공유하는 export (플러그인 공통 규약)
|
||||
Calc_Kanjub 31개 모듈
|
||||
___CPPdebugHook 2개 모듈
|
||||
Prn_Boq_Not 2개 모듈
|
||||
Prn_Nae_ColL 2개 모듈
|
||||
Prn_Nae_ColM 2개 모듈
|
||||
Prn_Nae_ColX 2개 모듈
|
||||
Prn_Nae_Cont1 2개 모듈
|
||||
Prn_Nae_Cont2 2개 모듈
|
||||
_MainWndProc@16 2개 모듈
|
||||
GetZipDllPrivVersion 1개 모듈
|
||||
GetZipDllVersion 1개 모듈
|
||||
ZipDllExec 1개 모듈
|
||||
@@ -0,0 +1,56 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
"""CPM 46개 모듈의 export 함수 전수 — 11번은 핵심 12개만 했음."""
|
||||
import sys, io, pathlib, struct, collections, re
|
||||
sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding="utf-8", errors="replace")
|
||||
ROOT = pathlib.Path(r"C:\경영정보(주)\System")
|
||||
|
||||
def exports(b):
|
||||
try:
|
||||
e=struct.unpack_from("<I",b,0x3C)[0]
|
||||
if b[e:e+4]!=b"PE\0\0": return []
|
||||
nsec=struct.unpack_from("<H",b,e+6)[0]; optsz=struct.unpack_from("<H",b,e+20)[0]
|
||||
opt=e+24; magic=struct.unpack_from("<H",b,opt)[0]
|
||||
dd=opt+(96 if magic==0x10b else 112)
|
||||
erva,esz=struct.unpack_from("<II",b,dd)
|
||||
if not erva: return []
|
||||
secs=[]; so=opt+optsz
|
||||
for i in range(nsec):
|
||||
s=b[so+i*40:so+i*40+40]
|
||||
vsz,va,rsz,ptr=struct.unpack_from("<IIII",s,8); secs.append((va,vsz,ptr,rsz))
|
||||
def r2o(r):
|
||||
for va,vsz,ptr,rsz in secs:
|
||||
if va<=r<va+max(vsz,rsz): return ptr+(r-va)
|
||||
eo=r2o(erva)
|
||||
if eo is None: return []
|
||||
nnames=struct.unpack_from("<I",b,eo+24)[0]
|
||||
namp=struct.unpack_from("<I",b,eo+32)[0]
|
||||
no=r2o(namp)
|
||||
out=[]
|
||||
for i in range(min(nnames,4000)):
|
||||
nr=struct.unpack_from("<I",b,no+4*i)[0]
|
||||
o=r2o(nr)
|
||||
if o is None: continue
|
||||
end=b.index(b"\0",o)
|
||||
out.append(b[o:end].decode("latin1"))
|
||||
return out
|
||||
except Exception: return []
|
||||
|
||||
per={}; allx=collections.Counter()
|
||||
for p in sorted(ROOT.rglob("*")):
|
||||
if not p.is_file() or p.suffix.upper() not in (".CPM",".EXE"): continue
|
||||
try: b=p.read_bytes()
|
||||
except Exception: continue
|
||||
if b[:2]!=b"MZ": continue
|
||||
x=exports(b)
|
||||
if x: per[p.name]=sorted(x)
|
||||
for n in x: allx[n]+=1
|
||||
|
||||
DONE={"ST_Boq.CPM","ST_EdiLWi.CPM","ST_KanJub.CPM","ST_SanCal.CPM","STmateQty8.CPM","ST_P_Joong.CPM",
|
||||
"ST_P_Collect.CPM","ST_P_ConEst.CPM","ST_U_ChgAmt.CPM","ST_U_ChgCode.CPM","ST_U_ConBD.CPM","ST_U_Convert.CPM"}
|
||||
print("### CPM/EXE export 전수 — 모듈 %d개, export %d개(중복포함)" % (len(per), sum(len(v) for v in per.values())))
|
||||
print(" 11번이 다룬 핵심 12개 말고 **%d개 모듈**이 남아 있었음\n" % len([k for k in per if k not in DONE]))
|
||||
for nm,x in sorted(per.items()):
|
||||
mark = "✅" if nm in DONE else " "
|
||||
print("%s %-22s %2d개 %s" % (mark, nm[:22], len(x), ", ".join(x)[:96]))
|
||||
print("\n### 여러 모듈이 공유하는 export (플러그인 공통 규약)")
|
||||
for n,c in allx.most_common(12): print(" %-22s %2d개 모듈" % (n,c))
|
||||
@@ -0,0 +1,49 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
"""변경 차수 저장 구조 — DBF 슬롯 4벌 vs 화면 8차의 어긋남을 가른다."""
|
||||
import sys, io, re, pathlib, zipfile, struct, collections
|
||||
sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding="utf-8", errors="replace")
|
||||
ROOT = pathlib.Path(r"D:\aislo-wt\sub\resources\knowledge\original\실무문서")
|
||||
|
||||
def fields(b):
|
||||
f=[];o=32
|
||||
while b[o]!=0x0D: f.append(b[o:o+11].rstrip(b"\0").decode("cp949","replace")); o+=32
|
||||
return f
|
||||
|
||||
print("### ① PRJLST.SMT 의 차수 섹션")
|
||||
for p in sorted(ROOT.rglob("*.STC")):
|
||||
try: z=zipfile.ZipFile(p); b=z.read("PRJLST.SMT")
|
||||
except Exception: continue
|
||||
secs=sorted({s for s in re.findall(r"\[([0-9]+)_KANJUB\]",
|
||||
"".join(ch for ch in b[0x200:].decode("cp949","replace")))}, key=int)
|
||||
print(" %-46s 섹션 %s" % (p.stem[:46], secs or "없음"))
|
||||
|
||||
print("\n### ② DBF 의 차수 슬롯 (접미사 숫자)")
|
||||
for p in list(sorted(ROOT.rglob("*.STC")))[:2]:
|
||||
z=zipfile.ZipFile(p)
|
||||
print("\n-- %s" % p.stem[:50])
|
||||
for t in ("PRJLST.DBF","BOQ11.DBF","COSTN.DBF"):
|
||||
try: f=fields(z.read(t))
|
||||
except Exception: continue
|
||||
sfx=collections.Counter()
|
||||
for n in f:
|
||||
m=re.search(r"(\d)$", n)
|
||||
if m: sfx[m.group(1)]+=1
|
||||
print(" %-12s 필드 %3d개 접미사별: %s" % (t, len(f), dict(sorted(sfx.items()))))
|
||||
|
||||
print("\n### ③ 화면·코드가 말하는 차수 상한")
|
||||
SYS=pathlib.Path(r"C:\경영정보(주)\System")
|
||||
pat=[rb"[1-9]\xec\xb0\xa8\xeb\xb3\x80\xea\xb2\xbd"] # UTF-8 'n차변경' — cp949 로 다시
|
||||
import re as _re
|
||||
need=[("%d차변경"%i).encode("cp949") for i in range(1,10)]
|
||||
hit=collections.Counter()
|
||||
for p in SYS.rglob("*"):
|
||||
if not p.is_file(): continue
|
||||
try: b=p.read_bytes()
|
||||
except Exception: continue
|
||||
if b[:2]!=b"MZ": continue
|
||||
for i,n in enumerate(need,1):
|
||||
if n in b: hit[i]+=1
|
||||
print(" 'n차변경' 문자열을 가진 모듈 수: %s" % dict(sorted(hit.items())))
|
||||
for tok in (b"BOQ1", b"BOQ2"):
|
||||
c=sum(1 for p in SYS.rglob("*") if p.is_file() and p.suffix.upper()==".CPM" and tok in p.read_bytes())
|
||||
print(" '%s' 를 가진 CPM 모듈 %d개" % (tok.decode(), c))
|
||||
@@ -62,6 +62,7 @@
|
||||
| 21 | **정정과 트랙 통합** — `SMT` 정정, 지식DB 세 트랙, 암호화의 성격 |
|
||||
| 22 | **UI 폼 분석** — 선택축 272개, 화면에 남아 있던 계산 규칙 |
|
||||
| 23 | **`COSTN.SMT` 전수파싱** — 단가산출 원장, Q식 10꼴, 운반 사이클 |
|
||||
| 24 | **모듈구조 전수** — 46개 export, 계산 공용 라이브러리 73함수, 동글 |
|
||||
|
||||
## 확정된 굵직한 것
|
||||
|
||||
|
||||
Reference in New Issue
Block a user