JIT ಬೆಂಬಲದೊಂದಿಗೆ Qemu.js: ನೀವು ಇನ್ನೂ ಕೊಚ್ಚು ಮಾಂಸವನ್ನು ಹಿಂದಕ್ಕೆ ತಿರುಗಿಸಬಹುದು

ಕೆಲವು ವರ್ಷಗಳ ಹಿಂದೆ ಫ್ಯಾಬ್ರಿಸ್ ಬೆಲ್ಲಾರ್ಡ್ jslinux ಬರೆದಿದ್ದಾರೆ JavaScript ನಲ್ಲಿ ಬರೆಯಲಾದ PC ಎಮ್ಯುಲೇಟರ್ ಆಗಿದೆ. ಅದರ ನಂತರ ಕನಿಷ್ಠ ಹೆಚ್ಚು ಇತ್ತು ವರ್ಚುವಲ್ x86. ಆದರೆ ಅವರೆಲ್ಲರೂ, ನನಗೆ ತಿಳಿದಿರುವಂತೆ, ವ್ಯಾಖ್ಯಾನಕಾರರಾಗಿದ್ದರು, ಆದರೆ ಅದೇ ಫ್ಯಾಬ್ರಿಸ್ ಬೆಲ್ಲಾರ್ಡ್‌ನಿಂದ ಬಹಳ ಹಿಂದೆಯೇ ಬರೆಯಲ್ಪಟ್ಟ ಕ್ವೆಮು ಮತ್ತು ಬಹುಶಃ ಯಾವುದೇ ಸ್ವಾಭಿಮಾನಿ ಆಧುನಿಕ ಎಮ್ಯುಲೇಟರ್, ಅತಿಥಿ ಕೋಡ್‌ನ ಜೆಐಟಿ ಸಂಕಲನವನ್ನು ಹೋಸ್ಟ್ ಸಿಸ್ಟಮ್ ಕೋಡ್‌ಗೆ ಬಳಸುತ್ತದೆ. ಬ್ರೌಸರ್‌ಗಳು ಪರಿಹರಿಸುವ ಒಂದಕ್ಕೆ ಸಂಬಂಧಿಸಿದಂತೆ ವಿರುದ್ಧವಾದ ಕೆಲಸವನ್ನು ಕಾರ್ಯಗತಗೊಳಿಸಲು ಇದು ಸಮಯ ಎಂದು ನನಗೆ ತೋರುತ್ತದೆ: ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್‌ಗೆ ಯಂತ್ರ ಕೋಡ್‌ನ JIT ಸಂಕಲನ, ಇದು ಪೋರ್ಟ್ Qemu ಗೆ ಹೆಚ್ಚು ತಾರ್ಕಿಕವಾಗಿ ಕಾಣುತ್ತದೆ. ಇದು ತೋರುತ್ತದೆ, ಏಕೆ Qemu, ಸರಳ ಮತ್ತು ಬಳಕೆದಾರ ಸ್ನೇಹಿ ಎಮ್ಯುಲೇಟರ್ಗಳು ಇವೆ - ಅದೇ ವರ್ಚುವಲ್ಬಾಕ್ಸ್, ಉದಾಹರಣೆಗೆ - ಸ್ಥಾಪಿಸಲಾಗಿದೆ ಮತ್ತು ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತದೆ. ಆದರೆ ಕ್ಯೂಮು ಹಲವಾರು ಆಸಕ್ತಿದಾಯಕ ವೈಶಿಷ್ಟ್ಯಗಳನ್ನು ಹೊಂದಿದೆ

  • ಮುಕ್ತ ಸಂಪನ್ಮೂಲ
  • ಕರ್ನಲ್ ಡ್ರೈವರ್ ಇಲ್ಲದೆ ಕೆಲಸ ಮಾಡುವ ಸಾಮರ್ಥ್ಯ
  • ಇಂಟರ್ಪ್ರಿಟರ್ ಮೋಡ್ನಲ್ಲಿ ಕೆಲಸ ಮಾಡುವ ಸಾಮರ್ಥ್ಯ
  • ಹೆಚ್ಚಿನ ಸಂಖ್ಯೆಯ ಹೋಸ್ಟ್ ಮತ್ತು ಅತಿಥಿ ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗಳಿಗೆ ಬೆಂಬಲ

ಮೂರನೆಯ ಅಂಶಕ್ಕೆ ಸಂಬಂಧಿಸಿದಂತೆ, ವಾಸ್ತವವಾಗಿ, TCI ಮೋಡ್‌ನಲ್ಲಿ, ಅತಿಥಿ ಯಂತ್ರದ ಸೂಚನೆಗಳನ್ನು ಸ್ವತಃ ಅರ್ಥೈಸಲಾಗುತ್ತದೆ ಎಂದು ನಾನು ಈಗ ವಿವರಿಸಬಲ್ಲೆ, ಆದರೆ ಅವುಗಳಿಂದ ಪಡೆದ ಬೈಟ್‌ಕೋಡ್, ಆದರೆ ಇದು ಸಾರವನ್ನು ಬದಲಾಯಿಸುವುದಿಲ್ಲ - ನಿರ್ಮಿಸಲು ಮತ್ತು ಚಲಾಯಿಸಲು ಹೊಸ ಆರ್ಕಿಟೆಕ್ಚರ್‌ನಲ್ಲಿ ಕ್ಯೂಮು, ನೀವು ಅದೃಷ್ಟವಂತರಾಗಿದ್ದರೆ, ಎ ಸಿ ಕಂಪೈಲರ್ ಸಾಕು - ಕೋಡ್ ಜನರೇಟರ್ ಬರೆಯುವುದನ್ನು ಮುಂದೂಡಬಹುದು.

ಮತ್ತು ಈಗ, ನನ್ನ ಬಿಡುವಿನ ವೇಳೆಯಲ್ಲಿ ಕ್ಯೂಮು ಮೂಲ ಕೋಡ್‌ನೊಂದಿಗೆ ನಿಧಾನವಾಗಿ ಟಿಂಕರ್ ಮಾಡಿದ ಎರಡು ವರ್ಷಗಳ ನಂತರ, ಕೆಲಸದ ಮೂಲಮಾದರಿಯು ಕಾಣಿಸಿಕೊಂಡಿತು, ಇದರಲ್ಲಿ ನೀವು ಈಗಾಗಲೇ ಚಲಾಯಿಸಬಹುದು, ಉದಾಹರಣೆಗೆ, ಕೊಲಿಬ್ರಿ ಓಎಸ್.

ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಎಂದರೇನು

ಇತ್ತೀಚಿನ ದಿನಗಳಲ್ಲಿ, ಅನೇಕ ಕಂಪೈಲರ್‌ಗಳು ಕಾಣಿಸಿಕೊಂಡಿವೆ, ಇದರ ಅಂತಿಮ ಫಲಿತಾಂಶವೆಂದರೆ ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್. ಕೆಲವು, ಟೈಪ್ ಸ್ಕ್ರಿಪ್ಟ್ ನಂತಹ, ಮೂಲತಃ ವೆಬ್‌ಗಾಗಿ ಬರೆಯಲು ಉತ್ತಮ ಮಾರ್ಗವೆಂದು ಉದ್ದೇಶಿಸಲಾಗಿತ್ತು. ಅದೇ ಸಮಯದಲ್ಲಿ, ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಅಸ್ತಿತ್ವದಲ್ಲಿರುವ C ಅಥವಾ C++ ಕೋಡ್ ಅನ್ನು ತೆಗೆದುಕೊಂಡು ಅದನ್ನು ಬ್ರೌಸರ್-ಓದಬಲ್ಲ ರೂಪದಲ್ಲಿ ಕಂಪೈಲ್ ಮಾಡಲು ಒಂದು ಮಾರ್ಗವಾಗಿದೆ. ಆನ್ ಈ ಪುಟ ನಾವು ಅನೇಕ ಪ್ರಸಿದ್ಧ ಕಾರ್ಯಕ್ರಮಗಳ ಬಂದರುಗಳನ್ನು ಸಂಗ್ರಹಿಸಿದ್ದೇವೆ: ಇಲ್ಲಿಉದಾಹರಣೆಗೆ, ನೀವು PyPy ಅನ್ನು ನೋಡಬಹುದು - ಮೂಲಕ, ಅವರು ಈಗಾಗಲೇ JIT ಅನ್ನು ಹೊಂದಿದ್ದಾರೆಂದು ಹೇಳಿಕೊಳ್ಳುತ್ತಾರೆ. ವಾಸ್ತವವಾಗಿ, ಪ್ರತಿ ಪ್ರೋಗ್ರಾಂ ಅನ್ನು ಸರಳವಾಗಿ ಕಂಪೈಲ್ ಮಾಡಲು ಮತ್ತು ಬ್ರೌಸರ್ನಲ್ಲಿ ರನ್ ಮಾಡಲು ಸಾಧ್ಯವಿಲ್ಲ - ಹಲವಾರು ಇವೆ ವೈಶಿಷ್ಟ್ಯಗಳು, ನೀವು ಇದನ್ನು ಸಹಿಸಿಕೊಳ್ಳಬೇಕು, ಆದಾಗ್ಯೂ, ಅದೇ ಪುಟದಲ್ಲಿರುವ ಶಾಸನವು ಹೇಳುವಂತೆ “ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಅನ್ನು ಬಹುತೇಕ ಯಾವುದೇ ಕಂಪೈಲ್ ಮಾಡಲು ಬಳಸಬಹುದು ಪೋರ್ಟಬಲ್ ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್‌ಗೆ C/C++ ಕೋಡ್". ಅಂದರೆ, ಸ್ಟ್ಯಾಂಡರ್ಡ್‌ಗೆ ಅನುಗುಣವಾಗಿ ವ್ಯಾಖ್ಯಾನಿಸದ ನಡವಳಿಕೆಯ ಹಲವಾರು ಕಾರ್ಯಾಚರಣೆಗಳಿವೆ, ಆದರೆ ಸಾಮಾನ್ಯವಾಗಿ x86 ನಲ್ಲಿ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತವೆ - ಉದಾಹರಣೆಗೆ, ವೇರಿಯೇಬಲ್‌ಗಳಿಗೆ ಜೋಡಿಸದ ಪ್ರವೇಶ, ಇದನ್ನು ಸಾಮಾನ್ಯವಾಗಿ ಕೆಲವು ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗಳಲ್ಲಿ ನಿಷೇಧಿಸಲಾಗಿದೆ. ಸಾಮಾನ್ಯವಾಗಿ , Qemu ಒಂದು ಕ್ರಾಸ್-ಪ್ಲಾಟ್‌ಫಾರ್ಮ್ ಪ್ರೋಗ್ರಾಂ ಮತ್ತು , ನಾನು ನಂಬಲು ಬಯಸುತ್ತೇನೆ, ಮತ್ತು ಇದು ಈಗಾಗಲೇ ಸಾಕಷ್ಟು ವ್ಯಾಖ್ಯಾನಿಸದ ನಡವಳಿಕೆಯನ್ನು ಹೊಂದಿಲ್ಲ - ಅದನ್ನು ತೆಗೆದುಕೊಂಡು ಕಂಪೈಲ್ ಮಾಡಿ, ನಂತರ JIT ಯೊಂದಿಗೆ ಸ್ವಲ್ಪ ಟಿಂಕರ್ ಮಾಡಿ - ಮತ್ತು ನೀವು ಮುಗಿಸಿದ್ದೀರಿ! ಆದರೆ ಅದು ಅಲ್ಲ ಪ್ರಕರಣ...

ಮೊದಲ ಪ್ರಯತ್ನ

ಸಾಮಾನ್ಯವಾಗಿ ಹೇಳುವುದಾದರೆ, ಕ್ಯೂಮುವನ್ನು ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್‌ಗೆ ಪೋರ್ಟ್ ಮಾಡುವ ಆಲೋಚನೆಯೊಂದಿಗೆ ಬಂದ ಮೊದಲ ವ್ಯಕ್ತಿ ನಾನಲ್ಲ. Emscripten ಅನ್ನು ಬಳಸಿಕೊಂಡು ಇದು ಸಾಧ್ಯವೇ ಎಂದು ReactOS ಫೋರಮ್‌ನಲ್ಲಿ ಪ್ರಶ್ನೆಯನ್ನು ಕೇಳಲಾಗಿದೆ. ಮುಂಚೆಯೇ, ಫ್ಯಾಬ್ರಿಸ್ ಬೆಲ್ಲಾರ್ಡ್ ಇದನ್ನು ವೈಯಕ್ತಿಕವಾಗಿ ಮಾಡಿದ್ದಾರೆ ಎಂಬ ವದಂತಿಗಳಿವೆ, ಆದರೆ ನಾವು jslinux ಬಗ್ಗೆ ಮಾತನಾಡುತ್ತಿದ್ದೇವೆ, ಇದು ನನಗೆ ತಿಳಿದಿರುವಂತೆ, JS ನಲ್ಲಿ ಸಾಕಷ್ಟು ಕಾರ್ಯಕ್ಷಮತೆಯನ್ನು ಹಸ್ತಚಾಲಿತವಾಗಿ ಸಾಧಿಸುವ ಪ್ರಯತ್ನವಾಗಿದೆ ಮತ್ತು ಅದನ್ನು ಮೊದಲಿನಿಂದ ಬರೆಯಲಾಗಿದೆ. ನಂತರ, ವರ್ಚುವಲ್ x86 ಅನ್ನು ಬರೆಯಲಾಯಿತು - ಅದಕ್ಕೆ ಅಸ್ಪಷ್ಟವಾದ ಮೂಲಗಳನ್ನು ಪೋಸ್ಟ್ ಮಾಡಲಾಗಿದೆ ಮತ್ತು ಹೇಳಿದಂತೆ, ಎಮ್ಯುಲೇಶನ್‌ನ ಹೆಚ್ಚಿನ “ವಾಸ್ತವಿಕತೆ” ಸೀಬಯೋಸ್ ಅನ್ನು ಫರ್ಮ್‌ವೇರ್ ಆಗಿ ಬಳಸಲು ಸಾಧ್ಯವಾಗಿಸಿತು. ಜೊತೆಗೆ, Emscripten ಅನ್ನು ಬಳಸಿಕೊಂಡು Qemu ಅನ್ನು ಪೋರ್ಟ್ ಮಾಡಲು ಕನಿಷ್ಠ ಒಂದು ಪ್ರಯತ್ನವಿದೆ - ನಾನು ಇದನ್ನು ಮಾಡಲು ಪ್ರಯತ್ನಿಸಿದೆ ಸಾಕೆಟ್ ಜೋಡಿ, ಆದರೆ ಅಭಿವೃದ್ಧಿ, ನಾನು ಅರ್ಥಮಾಡಿಕೊಂಡಂತೆ, ಫ್ರೀಜ್ ಆಗಿತ್ತು.

ಆದ್ದರಿಂದ, ಇದು ತೋರುತ್ತದೆ, ಇಲ್ಲಿ ಮೂಲಗಳು, ಇಲ್ಲಿ ಎಂಸ್ಕ್ರಿಪ್ಟನ್ - ಅದನ್ನು ತೆಗೆದುಕೊಂಡು ಕಂಪೈಲ್ ಮಾಡಿ. ಆದರೆ ಕ್ವೆಮು ಅವಲಂಬಿಸಿರುವ ಗ್ರಂಥಾಲಯಗಳು ಮತ್ತು ಆ ಗ್ರಂಥಾಲಯಗಳು ಅವಲಂಬಿಸಿರುವ ಗ್ರಂಥಾಲಯಗಳು ಇತ್ಯಾದಿಗಳೂ ಇವೆ, ಮತ್ತು ಅವುಗಳಲ್ಲಿ ಒಂದು libffi, ಯಾವ ಗ್ಲಿಬ್ ಅವಲಂಬಿಸಿರುತ್ತದೆ. ಎಮ್‌ಸ್ಕ್ರಿಪ್ಟನ್‌ಗಾಗಿ ಲೈಬ್ರರಿಗಳ ದೊಡ್ಡ ಸಂಗ್ರಹಣೆಯಲ್ಲಿ ಒಂದು ಇದೆ ಎಂದು ಇಂಟರ್ನೆಟ್‌ನಲ್ಲಿ ವದಂತಿಗಳಿವೆ, ಆದರೆ ಅದನ್ನು ನಂಬಲು ಹೇಗಾದರೂ ಕಷ್ಟವಾಯಿತು: ಮೊದಲನೆಯದಾಗಿ, ಇದು ಹೊಸ ಕಂಪೈಲರ್ ಆಗಲು ಉದ್ದೇಶಿಸಿರಲಿಲ್ಲ, ಎರಡನೆಯದಾಗಿ, ಇದು ತುಂಬಾ ಕಡಿಮೆ ಮಟ್ಟದ ಲೈಬ್ರರಿಯನ್ನು ತೆಗೆದುಕೊಳ್ಳಲು ಮತ್ತು JS ಗೆ ಕಂಪೈಲ್ ಮಾಡಲು. ಮತ್ತು ಇದು ಕೇವಲ ಅಸೆಂಬ್ಲಿ ಒಳಸೇರಿಸುವಿಕೆಯ ವಿಷಯವಲ್ಲ - ಬಹುಶಃ, ನೀವು ಅದನ್ನು ಟ್ವಿಸ್ಟ್ ಮಾಡಿದರೆ, ಕೆಲವು ಕರೆ ಸಂಪ್ರದಾಯಗಳಿಗೆ ನೀವು ಸ್ಟಾಕ್‌ನಲ್ಲಿ ಅಗತ್ಯವಾದ ಆರ್ಗ್ಯುಮೆಂಟ್‌ಗಳನ್ನು ರಚಿಸಬಹುದು ಮತ್ತು ಅವುಗಳಿಲ್ಲದೆ ಕಾರ್ಯವನ್ನು ಕರೆಯಬಹುದು. ಆದರೆ ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಒಂದು ಟ್ರಿಕಿ ವಿಷಯವಾಗಿದೆ: ರಚಿಸಲಾದ ಕೋಡ್ ಅನ್ನು ಬ್ರೌಸರ್ JS ಎಂಜಿನ್ ಆಪ್ಟಿಮೈಜರ್‌ಗೆ ಪರಿಚಿತವಾಗುವಂತೆ ಮಾಡಲು, ಕೆಲವು ತಂತ್ರಗಳನ್ನು ಬಳಸಲಾಗುತ್ತದೆ. ನಿರ್ದಿಷ್ಟವಾಗಿ, ರಿಲೂಪಿಂಗ್ ಎಂದು ಕರೆಯಲ್ಪಡುವ - ಸ್ವೀಕರಿಸಿದ LLVM IR ಅನ್ನು ಬಳಸುವ ಕೋಡ್ ಜನರೇಟರ್ ಕೆಲವು ಅಮೂರ್ತ ಪರಿವರ್ತನೆಯ ಸೂಚನೆಗಳೊಂದಿಗೆ ತೋರಿಕೆಯ ifs, ಲೂಪ್‌ಗಳು ಇತ್ಯಾದಿಗಳನ್ನು ಮರುಸೃಷ್ಟಿಸಲು ಪ್ರಯತ್ನಿಸುತ್ತದೆ. ಸರಿ, ವಾದಗಳನ್ನು ಕಾರ್ಯಕ್ಕೆ ಹೇಗೆ ರವಾನಿಸಲಾಗಿದೆ? ಸ್ವಾಭಾವಿಕವಾಗಿ, JS ಕಾರ್ಯಗಳಿಗೆ ವಾದಗಳು, ಅಂದರೆ, ಸಾಧ್ಯವಾದರೆ, ಸ್ಟಾಕ್ ಮೂಲಕ ಅಲ್ಲ.

ಆರಂಭದಲ್ಲಿ JS ನೊಂದಿಗೆ libffi ಗೆ ಬದಲಿ ಬರೆಯಲು ಮತ್ತು ಸ್ಟ್ಯಾಂಡರ್ಡ್ ಪರೀಕ್ಷೆಗಳನ್ನು ನಡೆಸುವ ಆಲೋಚನೆ ಇತ್ತು, ಆದರೆ ಕೊನೆಯಲ್ಲಿ ನನ್ನ ಹೆಡರ್ ಫೈಲ್‌ಗಳನ್ನು ಹೇಗೆ ತಯಾರಿಸುವುದು ಎಂಬುದರ ಕುರಿತು ಗೊಂದಲಕ್ಕೊಳಗಾಗಿದ್ದೇನೆ ಇದರಿಂದ ಅವು ಅಸ್ತಿತ್ವದಲ್ಲಿರುವ ಕೋಡ್‌ನೊಂದಿಗೆ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತವೆ - ನಾನು ಏನು ಮಾಡಬಹುದು, ಅವರು ಹೇಳುವಂತೆ, "ಕಾರ್ಯಗಳು ತುಂಬಾ ಸಂಕೀರ್ಣವಾಗಿದೆಯೇ "ನಾವು ತುಂಬಾ ಮೂರ್ಖರೇ?" ನಾನು ಲಿಬ್ಫಿಯನ್ನು ಮತ್ತೊಂದು ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗೆ ಪೋರ್ಟ್ ಮಾಡಬೇಕಾಗಿತ್ತು, ಆದ್ದರಿಂದ ಮಾತನಾಡಲು - ಅದೃಷ್ಟವಶಾತ್, ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಇನ್‌ಲೈನ್ ಅಸೆಂಬ್ಲಿಗಾಗಿ ಮ್ಯಾಕ್ರೋಗಳನ್ನು ಹೊಂದಿದೆ (ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್‌ನಲ್ಲಿ, ಹೌದು - ಅಲ್ಲದೆ, ಯಾವುದೇ ಆರ್ಕಿಟೆಕ್ಚರ್ ಆಗಿರಲಿ, ಆದ್ದರಿಂದ ಅಸೆಂಬ್ಲರ್), ಮತ್ತು ಫ್ಲೈನಲ್ಲಿ ರಚಿಸಲಾದ ಕೋಡ್ ಅನ್ನು ರನ್ ಮಾಡುವ ಸಾಮರ್ಥ್ಯ. ಸಾಮಾನ್ಯವಾಗಿ, ಸ್ವಲ್ಪ ಸಮಯದವರೆಗೆ ಪ್ಲಾಟ್‌ಫಾರ್ಮ್-ಅವಲಂಬಿತ ಲಿಬ್ಫಿ ತುಣುಕುಗಳೊಂದಿಗೆ ಟಿಂಕರ್ ಮಾಡಿದ ನಂತರ, ನಾನು ಕೆಲವು ಕಂಪೈಬಲ್ ಕೋಡ್ ಅನ್ನು ಪಡೆದುಕೊಂಡಿದ್ದೇನೆ ಮತ್ತು ನಾನು ಕಂಡ ಮೊದಲ ಪರೀಕ್ಷೆಯಲ್ಲಿ ಅದನ್ನು ಚಲಾಯಿಸಿದೆ. ನನ್ನ ಆಶ್ಚರ್ಯಕ್ಕೆ, ಪರೀಕ್ಷೆ ಯಶಸ್ವಿಯಾಗಿದೆ. ನನ್ನ ಪ್ರತಿಭೆಯಿಂದ ದಿಗ್ಭ್ರಮೆಗೊಂಡ - ತಮಾಷೆ ಇಲ್ಲ, ಇದು ಮೊದಲ ಉಡಾವಣೆಯಿಂದ ಕೆಲಸ ಮಾಡಿತು - ನಾನು, ಇನ್ನೂ ನನ್ನ ಕಣ್ಣುಗಳನ್ನು ನಂಬದೆ, ಫಲಿತಾಂಶದ ಕೋಡ್ ಅನ್ನು ಮತ್ತೆ ನೋಡಲು ಹೋದೆ, ಮುಂದೆ ಎಲ್ಲಿ ಅಗೆಯಬೇಕು ಎಂದು ಮೌಲ್ಯಮಾಪನ ಮಾಡಲು. ಇಲ್ಲಿ ನಾನು ಎರಡನೇ ಬಾರಿಗೆ ದಡ್ಡನಾಗಿದ್ದೇನೆ - ನನ್ನ ಕಾರ್ಯವು ಮಾಡಿದ್ದು ಒಂದೇ ffi_call - ಇದು ಯಶಸ್ವಿ ಕರೆಯನ್ನು ವರದಿ ಮಾಡಿದೆ. ಸ್ವತಃ ಯಾವುದೇ ಕರೆ ಇರಲಿಲ್ಲ. ಆದ್ದರಿಂದ ನಾನು ನನ್ನ ಮೊದಲ ಪುಲ್ ವಿನಂತಿಯನ್ನು ಕಳುಹಿಸಿದ್ದೇನೆ, ಇದು ಪರೀಕ್ಷೆಯಲ್ಲಿನ ದೋಷವನ್ನು ಸರಿಪಡಿಸಿದೆ ಅದು ಯಾವುದೇ ಒಲಿಂಪಿಯಾಡ್ ವಿದ್ಯಾರ್ಥಿಗೆ ಸ್ಪಷ್ಟವಾಗಿದೆ - ನೈಜ ಸಂಖ್ಯೆಗಳನ್ನು ಹೋಲಿಸಬಾರದು a == b ಮತ್ತು ಹೇಗೆ a - b < EPS - ನೀವು ಮಾಡ್ಯೂಲ್ ಅನ್ನು ಸಹ ನೆನಪಿಟ್ಟುಕೊಳ್ಳಬೇಕು, ಇಲ್ಲದಿದ್ದರೆ 0 1/3 ಗೆ ಸಮನಾಗಿರುತ್ತದೆ ... ಸಾಮಾನ್ಯವಾಗಿ, ನಾನು ಲಿಬ್ಫಿಯ ಒಂದು ನಿರ್ದಿಷ್ಟ ಪೋರ್ಟ್ನೊಂದಿಗೆ ಬಂದಿದ್ದೇನೆ, ಇದು ಸರಳವಾದ ಪರೀಕ್ಷೆಗಳನ್ನು ಹಾದುಹೋಗುತ್ತದೆ ಮತ್ತು ಯಾವ ಗ್ಲಿಬ್ನೊಂದಿಗೆ ಇರುತ್ತದೆ. ಸಂಕಲಿಸಲಾಗಿದೆ - ಇದು ಅಗತ್ಯ ಎಂದು ನಾನು ನಿರ್ಧರಿಸಿದೆ, ನಾನು ಅದನ್ನು ನಂತರ ಸೇರಿಸುತ್ತೇನೆ. ಮುಂದೆ ನೋಡುವಾಗ, ನಾನು ಹೇಳುತ್ತೇನೆ, ಅದು ಬದಲಾದಂತೆ, ಕಂಪೈಲರ್ ಅಂತಿಮ ಕೋಡ್‌ನಲ್ಲಿ libffi ಕಾರ್ಯವನ್ನು ಸಹ ಸೇರಿಸಲಿಲ್ಲ.

ಆದರೆ, ನಾನು ಈಗಾಗಲೇ ಹೇಳಿದಂತೆ, ಕೆಲವು ಮಿತಿಗಳಿವೆ, ಮತ್ತು ವಿವಿಧ ವ್ಯಾಖ್ಯಾನಿಸದ ನಡವಳಿಕೆಯ ಉಚಿತ ಬಳಕೆಯ ನಡುವೆ, ಹೆಚ್ಚು ಅಹಿತಕರ ವೈಶಿಷ್ಟ್ಯವನ್ನು ಮರೆಮಾಡಲಾಗಿದೆ - ವಿನ್ಯಾಸದ ಮೂಲಕ ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್ ಹಂಚಿಕೆಯ ಮೆಮೊರಿಯೊಂದಿಗೆ ಮಲ್ಟಿಥ್ರೆಡಿಂಗ್ ಅನ್ನು ಬೆಂಬಲಿಸುವುದಿಲ್ಲ. ತಾತ್ವಿಕವಾಗಿ, ಇದನ್ನು ಸಾಮಾನ್ಯವಾಗಿ ಒಳ್ಳೆಯ ಕಲ್ಪನೆ ಎಂದೂ ಕರೆಯಬಹುದು, ಆದರೆ ಸಿ ಥ್ರೆಡ್‌ಗಳಿಗೆ ಆರ್ಕಿಟೆಕ್ಚರ್ ಅನ್ನು ಜೋಡಿಸಲಾದ ಪೋರ್ಟಿಂಗ್ ಕೋಡ್‌ಗೆ ಅಲ್ಲ. ಸಾಮಾನ್ಯವಾಗಿ ಹೇಳುವುದಾದರೆ, ಫೈರ್‌ಫಾಕ್ಸ್ ಹಂಚಿದ ಕೆಲಸಗಾರರನ್ನು ಬೆಂಬಲಿಸುವ ಪ್ರಯೋಗವನ್ನು ಮಾಡುತ್ತಿದೆ ಮತ್ತು ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಅವರಿಗೆ pthread ಅನುಷ್ಠಾನವನ್ನು ಹೊಂದಿದೆ, ಆದರೆ ನಾನು ಅದನ್ನು ಅವಲಂಬಿಸಲು ಬಯಸಲಿಲ್ಲ. ನಾನು Qemu ಕೋಡ್‌ನಿಂದ ಮಲ್ಟಿಥ್ರೆಡಿಂಗ್ ಅನ್ನು ನಿಧಾನವಾಗಿ ಬೇರುಬಿಡಬೇಕಾಗಿತ್ತು - ಅಂದರೆ, ಥ್ರೆಡ್‌ಗಳು ಎಲ್ಲಿ ಚಲಿಸುತ್ತಿವೆ ಎಂಬುದನ್ನು ಕಂಡುಹಿಡಿಯಿರಿ, ಈ ಥ್ರೆಡ್‌ನಲ್ಲಿ ಚಾಲನೆಯಲ್ಲಿರುವ ಲೂಪ್‌ನ ದೇಹವನ್ನು ಪ್ರತ್ಯೇಕ ಕಾರ್ಯಕ್ಕೆ ಸರಿಸಿ ಮತ್ತು ಅಂತಹ ಕಾರ್ಯಗಳನ್ನು ಮುಖ್ಯ ಲೂಪ್‌ನಿಂದ ಒಂದೊಂದಾಗಿ ಕರೆ ಮಾಡಿ.

ಎರಡನೆಯ ಪ್ರಯತ್ನ

ಕೆಲವು ಹಂತದಲ್ಲಿ, ಸಮಸ್ಯೆ ಇನ್ನೂ ಇದೆ ಎಂದು ಸ್ಪಷ್ಟವಾಯಿತು, ಮತ್ತು ಕೋಡ್ ಸುತ್ತಲೂ ಅಡ್ಡಾದಿಡ್ಡಿಯಾಗಿ ಊರುಗೋಲನ್ನು ತಳ್ಳುವುದು ಯಾವುದೇ ಒಳ್ಳೆಯದಕ್ಕೆ ಕಾರಣವಾಗುವುದಿಲ್ಲ. ತೀರ್ಮಾನ: ಊರುಗೋಲನ್ನು ಸೇರಿಸುವ ಪ್ರಕ್ರಿಯೆಯನ್ನು ನಾವು ಹೇಗಾದರೂ ವ್ಯವಸ್ಥಿತಗೊಳಿಸಬೇಕಾಗಿದೆ. ಆದ್ದರಿಂದ, ಆ ಸಮಯದಲ್ಲಿ ತಾಜಾವಾಗಿದ್ದ ಆವೃತ್ತಿ 2.4.1 ಅನ್ನು ತೆಗೆದುಕೊಳ್ಳಲಾಗಿದೆ (2.5.0 ಅಲ್ಲ, ಏಕೆಂದರೆ, ಯಾರಿಗೆ ತಿಳಿದಿದೆ, ಹೊಸ ಆವೃತ್ತಿಯಲ್ಲಿ ಇನ್ನೂ ಸಿಕ್ಕಿಹಾಕಿಕೊಳ್ಳದ ದೋಷಗಳು ಇರುತ್ತವೆ ಮತ್ತು ನನ್ನ ಸ್ವಂತ ದೋಷಗಳು ಸಾಕಷ್ಟು ಇವೆ ), ಮತ್ತು ಮೊದಲನೆಯದು ಅದನ್ನು ಸುರಕ್ಷಿತವಾಗಿ ಪುನಃ ಬರೆಯುವುದು thread-posix.c. ಒಳ್ಳೆಯದು, ಅಂದರೆ, ಸುರಕ್ಷಿತವಾಗಿದೆ: ಯಾರಾದರೂ ನಿರ್ಬಂಧಿಸಲು ಕಾರಣವಾಗುವ ಕಾರ್ಯಾಚರಣೆಯನ್ನು ಮಾಡಲು ಪ್ರಯತ್ನಿಸಿದರೆ, ಕಾರ್ಯವನ್ನು ತಕ್ಷಣವೇ ಕರೆಯಲಾಯಿತು abort() - ಸಹಜವಾಗಿ, ಇದು ಎಲ್ಲಾ ಸಮಸ್ಯೆಗಳನ್ನು ಏಕಕಾಲದಲ್ಲಿ ಪರಿಹರಿಸಲಿಲ್ಲ, ಆದರೆ ಅಸಮಂಜಸವಾದ ಡೇಟಾವನ್ನು ಸದ್ದಿಲ್ಲದೆ ಸ್ವೀಕರಿಸುವುದಕ್ಕಿಂತ ಇದು ಹೇಗಾದರೂ ಹೆಚ್ಚು ಆಹ್ಲಾದಕರವಾಗಿರುತ್ತದೆ.

ಸಾಮಾನ್ಯವಾಗಿ, JS ಗೆ ಕೋಡ್ ಅನ್ನು ಪೋರ್ಟ್ ಮಾಡಲು ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಆಯ್ಕೆಗಳು ತುಂಬಾ ಸಹಾಯಕವಾಗಿವೆ -s ASSERTIONS=1 -s SAFE_HEAP=1 - ಅವರು ಕೆಲವು ರೀತಿಯ ವ್ಯಾಖ್ಯಾನಿಸದ ನಡವಳಿಕೆಯನ್ನು ಹಿಡಿಯುತ್ತಾರೆ, ಉದಾಹರಣೆಗೆ ಜೋಡಿಸದ ವಿಳಾಸಕ್ಕೆ ಕರೆಗಳು (ಇದು ಟೈಪ್ ಮಾಡಿದ ಅರೇಗಳ ಕೋಡ್‌ಗೆ ಹೊಂದಿಕೆಯಾಗುವುದಿಲ್ಲ HEAP32[addr >> 2] = 1) ಅಥವಾ ತಪ್ಪಾದ ಸಂಖ್ಯೆಯ ಆರ್ಗ್ಯುಮೆಂಟ್‌ಗಳೊಂದಿಗೆ ಕಾರ್ಯವನ್ನು ಕರೆಯುವುದು.

ಮೂಲಕ, ಜೋಡಣೆ ದೋಷಗಳು ಪ್ರತ್ಯೇಕ ಸಮಸ್ಯೆಯಾಗಿದೆ. ನಾನು ಈಗಾಗಲೇ ಹೇಳಿದಂತೆ, ಕೋಡ್ ಉತ್ಪಾದನೆ TCI (ಸಣ್ಣ ಕೋಡ್ ಇಂಟರ್ಪ್ರಿಟರ್) ಗಾಗಿ Qemu "ಕ್ಷೀಣಗೊಳ್ಳುವ" ವಿವರಣಾತ್ಮಕ ಬ್ಯಾಕೆಂಡ್ ಅನ್ನು ಹೊಂದಿದೆ ಮತ್ತು ಹೊಸ ಆರ್ಕಿಟೆಕ್ಚರ್ನಲ್ಲಿ Qemu ಅನ್ನು ನಿರ್ಮಿಸಲು ಮತ್ತು ಚಲಾಯಿಸಲು, ನೀವು ಅದೃಷ್ಟವಂತರಾಗಿದ್ದರೆ, C ಕಂಪೈಲರ್ ಸಾಕು. ಕೀವರ್ಡ್ಗಳು "ನೀವು ಅದೃಷ್ಟವಂತರಾಗಿದ್ದರೆ". ನಾನು ದುರದೃಷ್ಟವಂತ, ಮತ್ತು TCI ತನ್ನ ಬೈಟ್‌ಕೋಡ್ ಅನ್ನು ಪಾರ್ಸ್ ಮಾಡುವಾಗ ಜೋಡಿಸದ ಪ್ರವೇಶವನ್ನು ಬಳಸುತ್ತದೆ ಎಂದು ಅದು ಬದಲಾಯಿತು. ಅಂದರೆ, ಎಲ್ಲಾ ರೀತಿಯ ARM ಮತ್ತು ಇತರ ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗಳಲ್ಲಿ ಅಗತ್ಯವಾಗಿ ಸಮತಟ್ಟಾದ ಪ್ರವೇಶದೊಂದಿಗೆ, Qemu ಕಂಪೈಲ್ ಮಾಡುತ್ತದೆ ಏಕೆಂದರೆ ಅವುಗಳು ಸ್ಥಳೀಯ ಕೋಡ್ ಅನ್ನು ಉತ್ಪಾದಿಸುವ ಸಾಮಾನ್ಯ TCG ಬ್ಯಾಕೆಂಡ್ ಅನ್ನು ಹೊಂದಿರುತ್ತವೆ, ಆದರೆ TCI ಅವುಗಳ ಮೇಲೆ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತದೆಯೇ ಎಂಬುದು ಮತ್ತೊಂದು ಪ್ರಶ್ನೆಯಾಗಿದೆ. ಆದಾಗ್ಯೂ, ಅದು ಬದಲಾದಂತೆ, TCI ದಸ್ತಾವೇಜನ್ನು ಸ್ಪಷ್ಟವಾಗಿ ಇದೇ ರೀತಿಯದನ್ನು ಸೂಚಿಸುತ್ತದೆ. ಇದರ ಪರಿಣಾಮವಾಗಿ, ಅಲೈನ್ ಮಾಡದ ಓದುವಿಕೆಗಾಗಿ ಫಂಕ್ಷನ್ ಕರೆಗಳನ್ನು ಕೋಡ್‌ಗೆ ಸೇರಿಸಲಾಯಿತು, ಇದನ್ನು ಕ್ವಿಮುವಿನ ಇನ್ನೊಂದು ಭಾಗದಲ್ಲಿ ಕಂಡುಹಿಡಿಯಲಾಯಿತು.

ರಾಶಿ ವಿನಾಶ

ಪರಿಣಾಮವಾಗಿ, TCI ಗೆ ಜೋಡಿಸದ ಪ್ರವೇಶವನ್ನು ಸರಿಪಡಿಸಲಾಗಿದೆ, ಮುಖ್ಯ ಲೂಪ್ ಅನ್ನು ರಚಿಸಲಾಗಿದೆ, ಅದನ್ನು ಪ್ರೊಸೆಸರ್, RCU ಮತ್ತು ಇತರ ಕೆಲವು ಸಣ್ಣ ವಿಷಯಗಳನ್ನು ಕರೆಯಲಾಗುತ್ತದೆ. ಹಾಗಾಗಿ ನಾನು ಆಯ್ಕೆಯೊಂದಿಗೆ Qemu ಅನ್ನು ಪ್ರಾರಂಭಿಸುತ್ತೇನೆ -d exec,in_asm,out_asm, ಅಂದರೆ ಯಾವ ಕೋಡ್ ಬ್ಲಾಕ್‌ಗಳನ್ನು ಕಾರ್ಯಗತಗೊಳಿಸಲಾಗುತ್ತಿದೆ ಎಂದು ನೀವು ಹೇಳಬೇಕು ಮತ್ತು ಪ್ರಸಾರದ ಸಮಯದಲ್ಲಿ ಅತಿಥಿ ಕೋಡ್ ಯಾವುದು, ಹೋಸ್ಟ್ ಕೋಡ್ ಏನಾಯಿತು (ಈ ಸಂದರ್ಭದಲ್ಲಿ ಬೈಟ್‌ಕೋಡ್) ಬರೆಯಲು ಸಹ ನೀವು ಹೇಳಬೇಕು. ಇದು ಪ್ರಾರಂಭವಾಗುತ್ತದೆ, ಹಲವಾರು ಅನುವಾದ ಬ್ಲಾಕ್‌ಗಳನ್ನು ಕಾರ್ಯಗತಗೊಳಿಸುತ್ತದೆ, RCU ಈಗ ಪ್ರಾರಂಭವಾಗಲಿದೆ ಎಂದು ನಾನು ಬಿಟ್ಟ ಡೀಬಗ್ ಮಾಡುವ ಸಂದೇಶವನ್ನು ಬರೆಯುತ್ತದೆ ಮತ್ತು... ಕ್ರ್ಯಾಶ್ ಆಗುತ್ತದೆ abort() ಒಂದು ಕಾರ್ಯದ ಒಳಗೆ free(). ಕಾರ್ಯವನ್ನು ಟಿಂಕರ್ ಮಾಡುವ ಮೂಲಕ free() ಹೀಪ್ ಬ್ಲಾಕ್‌ನ ಹೆಡರ್‌ನಲ್ಲಿ, ನಿಗದಿಪಡಿಸಿದ ಮೆಮೊರಿಯ ಹಿಂದಿನ ಎಂಟು ಬೈಟ್‌ಗಳಲ್ಲಿ, ಬ್ಲಾಕ್ ಗಾತ್ರ ಅಥವಾ ಅದೇ ರೀತಿಯ ಬದಲಿಗೆ, ಕಸವಿದೆ ಎಂದು ನಾವು ಕಂಡುಹಿಡಿಯುವಲ್ಲಿ ಯಶಸ್ವಿಯಾಗಿದ್ದೇವೆ.

ರಾಶಿಯ ವಿನಾಶ - ಎಷ್ಟು ಮುದ್ದಾಗಿದೆ ... ಅಂತಹ ಸಂದರ್ಭದಲ್ಲಿ, ಒಂದು ಉಪಯುಕ್ತ ಪರಿಹಾರವಿದೆ - (ಸಾಧ್ಯವಾದರೆ) ಅದೇ ಮೂಲಗಳಿಂದ, ಸ್ಥಳೀಯ ಬೈನರಿಯನ್ನು ಜೋಡಿಸಿ ಮತ್ತು ವಾಲ್ಗ್ರಿಂಡ್ ಅಡಿಯಲ್ಲಿ ಚಲಾಯಿಸಿ. ಸ್ವಲ್ಪ ಸಮಯದ ನಂತರ, ಬೈನರಿ ಸಿದ್ಧವಾಯಿತು. ನಾನು ಅದೇ ಆಯ್ಕೆಗಳೊಂದಿಗೆ ಅದನ್ನು ಪ್ರಾರಂಭಿಸುತ್ತೇನೆ - ಇದು ವಾಸ್ತವವಾಗಿ ಮರಣದಂಡನೆಯನ್ನು ತಲುಪುವ ಮೊದಲು ಪ್ರಾರಂಭದ ಸಮಯದಲ್ಲಿ ಸಹ ಕ್ರ್ಯಾಶ್ ಆಗುತ್ತದೆ. ಇದು ಅಹಿತಕರವಾಗಿದೆ, ಸಹಜವಾಗಿ - ಸ್ಪಷ್ಟವಾಗಿ, ಮೂಲಗಳು ಒಂದೇ ಆಗಿರಲಿಲ್ಲ, ಇದು ಆಶ್ಚರ್ಯವೇನಿಲ್ಲ, ಏಕೆಂದರೆ ಕಾನ್ಫಿಗರ್ ಸ್ವಲ್ಪ ವಿಭಿನ್ನ ಆಯ್ಕೆಗಳನ್ನು ಸ್ಕೌಟ್ ಮಾಡಲಾಗಿದೆ, ಆದರೆ ನಾನು ವಾಲ್ಗ್ರಿಂಡ್ ಅನ್ನು ಹೊಂದಿದ್ದೇನೆ - ಮೊದಲು ನಾನು ಈ ದೋಷವನ್ನು ಸರಿಪಡಿಸುತ್ತೇನೆ ಮತ್ತು ನಂತರ, ನಾನು ಅದೃಷ್ಟವಂತನಾಗಿದ್ದರೆ , ಮೂಲವು ಕಾಣಿಸಿಕೊಳ್ಳುತ್ತದೆ. ನಾನು Valgrind ಅಡಿಯಲ್ಲಿ ಅದೇ ವಿಷಯವನ್ನು ಚಲಾಯಿಸುತ್ತಿದ್ದೇನೆ... Y-y-y, y-y-y, uh-uh, ಇದು ಪ್ರಾರಂಭವಾಯಿತು, ಸಾಮಾನ್ಯವಾಗಿ ಪ್ರಾರಂಭದ ಮೂಲಕ ಹೋಯಿತು ಮತ್ತು ತಪ್ಪಾದ ಮೆಮೊರಿ ಪ್ರವೇಶದ ಬಗ್ಗೆ ಒಂದೇ ಎಚ್ಚರಿಕೆಯಿಲ್ಲದೆ ಮೂಲ ದೋಷವನ್ನು ಕಳೆದಿದೆ, ಫಾಲ್ಸ್ ಬಗ್ಗೆ ಉಲ್ಲೇಖಿಸಬಾರದು. ಜೀವನ, ಅವರು ಹೇಳಿದಂತೆ, ಇದಕ್ಕಾಗಿ ನನ್ನನ್ನು ಸಿದ್ಧಪಡಿಸಲಿಲ್ಲ - ವಾಲ್ಗ್ರಿಂಡ್ ಅಡಿಯಲ್ಲಿ ಪ್ರಾರಂಭಿಸಿದಾಗ ಕ್ರ್ಯಾಶಿಂಗ್ ಪ್ರೋಗ್ರಾಂ ಕ್ರ್ಯಾಶ್ ಆಗುವುದನ್ನು ನಿಲ್ಲಿಸುತ್ತದೆ. ಅದು ಏನಾಗಿತ್ತು ಎಂಬುದು ನಿಗೂಢ. ನನ್ನ ಊಹೆಯೆಂದರೆ, ಪ್ರಾರಂಭದ ಸಮಯದಲ್ಲಿ ಕುಸಿತದ ನಂತರ ಪ್ರಸ್ತುತ ಸೂಚನೆಯ ಸಮೀಪದಲ್ಲಿ ಒಮ್ಮೆ, gdb ಕೆಲಸವನ್ನು ತೋರಿಸಿದೆ memset-ಒಂದು ಮಾನ್ಯವಾದ ಪಾಯಿಂಟರ್ ಅನ್ನು ಬಳಸಿ mmx, ಅಥವಾ xmm ನೋಂದಾಯಿಸುತ್ತದೆ, ನಂತರ ಬಹುಶಃ ಇದು ಕೆಲವು ರೀತಿಯ ಜೋಡಣೆ ದೋಷವಾಗಿದೆ, ಆದರೂ ನಂಬಲು ಇನ್ನೂ ಕಷ್ಟ.

ಸರಿ, Valgrind ಇಲ್ಲಿ ಸಹಾಯ ಮಾಡುವಂತೆ ತೋರುತ್ತಿಲ್ಲ. ಮತ್ತು ಇಲ್ಲಿ ಅತ್ಯಂತ ಅಸಹ್ಯಕರ ವಿಷಯ ಪ್ರಾರಂಭವಾಯಿತು - ಎಲ್ಲವೂ ಪ್ರಾರಂಭವಾದಂತೆ ತೋರುತ್ತದೆ, ಆದರೆ ಲಕ್ಷಾಂತರ ಸೂಚನೆಗಳ ಹಿಂದೆ ಸಂಭವಿಸಬಹುದಾದ ಘಟನೆಯಿಂದಾಗಿ ಸಂಪೂರ್ಣವಾಗಿ ಅಪರಿಚಿತ ಕಾರಣಗಳಿಗಾಗಿ ಕ್ರ್ಯಾಶ್ ಆಗುತ್ತದೆ. ದೀರ್ಘಕಾಲದವರೆಗೆ, ಹೇಗೆ ಸಮೀಪಿಸಬೇಕೆಂದು ಸಹ ಸ್ಪಷ್ಟವಾಗಿಲ್ಲ. ಕೊನೆಯಲ್ಲಿ, ನಾನು ಇನ್ನೂ ಕುಳಿತು ಡೀಬಗ್ ಮಾಡಬೇಕಾಗಿತ್ತು. ಹೆಡರ್ ಅನ್ನು ಪುನಃ ಬರೆಯಲಾಗಿದೆ ಎಂಬುದನ್ನು ಮುದ್ರಿಸುವುದು ಅದು ಸಂಖ್ಯೆಯಂತೆ ಕಾಣುತ್ತಿಲ್ಲ, ಬದಲಿಗೆ ಕೆಲವು ರೀತಿಯ ಬೈನರಿ ಡೇಟಾ ಎಂದು ತೋರಿಸಿದೆ. ಮತ್ತು, ಇಗೋ, ಈ ಬೈನರಿ ಸ್ಟ್ರಿಂಗ್ BIOS ಫೈಲ್‌ನಲ್ಲಿ ಕಂಡುಬಂದಿದೆ - ಅಂದರೆ, ಈಗ ಅದು ಬಫರ್ ಓವರ್‌ಫ್ಲೋ ಎಂದು ಸಮಂಜಸವಾದ ವಿಶ್ವಾಸದಿಂದ ಹೇಳಲು ಸಾಧ್ಯವಾಯಿತು ಮತ್ತು ಅದನ್ನು ಈ ಬಫರ್‌ಗೆ ಬರೆಯಲಾಗಿದೆ ಎಂಬುದು ಸ್ಪಷ್ಟವಾಗಿದೆ. ಸರಿ, ನಂತರ ಈ ರೀತಿಯದ್ದು - ಎಂಸ್ಕ್ರಿಪ್ಟನ್‌ನಲ್ಲಿ, ಅದೃಷ್ಟವಶಾತ್, ವಿಳಾಸ ಸ್ಥಳದ ಯಾವುದೇ ಯಾದೃಚ್ಛಿಕತೆ ಇಲ್ಲ, ಅದರಲ್ಲಿ ಯಾವುದೇ ರಂಧ್ರಗಳಿಲ್ಲ, ಆದ್ದರಿಂದ ನೀವು ಕೊನೆಯ ಉಡಾವಣೆಯಿಂದ ಪಾಯಿಂಟರ್ ಮೂಲಕ ಡೇಟಾವನ್ನು ಔಟ್‌ಪುಟ್ ಮಾಡಲು ಕೋಡ್‌ನ ಮಧ್ಯದಲ್ಲಿ ಎಲ್ಲೋ ಬರೆಯಬಹುದು, ಡೇಟಾವನ್ನು ನೋಡಿ, ಪಾಯಿಂಟರ್ ಅನ್ನು ನೋಡಿ, ಮತ್ತು ಅದು ಬದಲಾಗದಿದ್ದರೆ, ಆಲೋಚನೆಗೆ ಆಹಾರವನ್ನು ಪಡೆಯಿರಿ. ನಿಜ, ಯಾವುದೇ ಬದಲಾವಣೆಯ ನಂತರ ಲಿಂಕ್ ಮಾಡಲು ಒಂದೆರಡು ನಿಮಿಷಗಳನ್ನು ತೆಗೆದುಕೊಳ್ಳುತ್ತದೆ, ಆದರೆ ನೀವು ಏನು ಮಾಡಬಹುದು? ಪರಿಣಾಮವಾಗಿ, ತಾತ್ಕಾಲಿಕ ಬಫರ್‌ನಿಂದ ಅತಿಥಿ ಮೆಮೊರಿಗೆ BIOS ಅನ್ನು ನಕಲಿಸುವ ಒಂದು ನಿರ್ದಿಷ್ಟ ಸಾಲು ಕಂಡುಬಂದಿದೆ - ಮತ್ತು, ವಾಸ್ತವವಾಗಿ, ಬಫರ್‌ನಲ್ಲಿ ಸಾಕಷ್ಟು ಸ್ಥಳವಿಲ್ಲ. ಆ ವಿಚಿತ್ರ ಬಫರ್ ವಿಳಾಸದ ಮೂಲವನ್ನು ಕಂಡುಹಿಡಿಯುವುದು ಒಂದು ಕಾರ್ಯಕ್ಕೆ ಕಾರಣವಾಯಿತು qemu_anon_ram_alloc ಕಡತದಲ್ಲಿ oslib-posix.c - ತರ್ಕ ಹೀಗಿತ್ತು: ಕೆಲವೊಮ್ಮೆ ವಿಳಾಸವನ್ನು 2 MB ಗಾತ್ರದ ದೊಡ್ಡ ಪುಟಕ್ಕೆ ಜೋಡಿಸಲು ಇದು ಉಪಯುಕ್ತವಾಗಿದೆ, ಇದಕ್ಕಾಗಿ ನಾವು ಕೇಳುತ್ತೇವೆ mmap ಮೊದಲು ಸ್ವಲ್ಪ ಹೆಚ್ಚು, ಮತ್ತು ನಂತರ ನಾವು ಸಹಾಯದಿಂದ ಹೆಚ್ಚುವರಿ ಹಿಂತಿರುಗಿಸುತ್ತೇವೆ munmap. ಮತ್ತು ಅಂತಹ ಜೋಡಣೆ ಅಗತ್ಯವಿಲ್ಲದಿದ್ದರೆ, ನಾವು 2 MB ಬದಲಿಗೆ ಫಲಿತಾಂಶವನ್ನು ಸೂಚಿಸುತ್ತೇವೆ getpagesize() - mmap ಇದು ಇನ್ನೂ ಜೋಡಿಸಲಾದ ವಿಳಾಸವನ್ನು ನೀಡುತ್ತದೆ... ಆದ್ದರಿಂದ ಎಂಸ್ಕ್ರಿಪ್ಟನ್‌ನಲ್ಲಿ mmap ಕೇವಲ ಕರೆಗಳು malloc, ಆದರೆ ಸಹಜವಾಗಿ ಇದು ಪುಟದಲ್ಲಿ ಜೋಡಿಸುವುದಿಲ್ಲ. ಸಾಮಾನ್ಯವಾಗಿ, ಒಂದೆರಡು ತಿಂಗಳ ಕಾಲ ನನ್ನನ್ನು ನಿರಾಶೆಗೊಳಿಸಿದ ದೋಷವನ್ನು ಬದಲಾವಣೆಯಿಂದ ಸರಿಪಡಿಸಲಾಗಿದೆ двух ಸಾಲುಗಳು.

ಕರೆ ಕಾರ್ಯಗಳ ವೈಶಿಷ್ಟ್ಯಗಳು

ಮತ್ತು ಈಗ ಪ್ರೊಸೆಸರ್ ಏನನ್ನಾದರೂ ಎಣಿಸುತ್ತಿದೆ, Qemu ಕ್ರ್ಯಾಶ್ ಆಗುವುದಿಲ್ಲ, ಆದರೆ ಪರದೆಯು ಆನ್ ಆಗುವುದಿಲ್ಲ, ಮತ್ತು ಪ್ರೊಸೆಸರ್ ತ್ವರಿತವಾಗಿ ಲೂಪ್ಗಳಿಗೆ ಹೋಗುತ್ತದೆ, ಔಟ್ಪುಟ್ ಮೂಲಕ ನಿರ್ಣಯಿಸುತ್ತದೆ -d exec,in_asm,out_asm. ಒಂದು ಊಹೆ ಹೊರಹೊಮ್ಮಿದೆ: ಟೈಮರ್ ಅಡಚಣೆಗಳು (ಅಥವಾ, ಸಾಮಾನ್ಯವಾಗಿ, ಎಲ್ಲಾ ಅಡಚಣೆಗಳು) ಬರುವುದಿಲ್ಲ. ಮತ್ತು ವಾಸ್ತವವಾಗಿ, ಕೆಲವು ಕಾರಣಗಳಿಂದ ಕೆಲಸ ಮಾಡಿದ ಸ್ಥಳೀಯ ಅಸೆಂಬ್ಲಿಯಿಂದ ನೀವು ಅಡಚಣೆಗಳನ್ನು ತಿರುಗಿಸಿದರೆ, ನೀವು ಇದೇ ರೀತಿಯ ಚಿತ್ರವನ್ನು ಪಡೆಯುತ್ತೀರಿ. ಆದರೆ ಇದು ಎಲ್ಲಕ್ಕೂ ಉತ್ತರವಲ್ಲ: ಮೇಲಿನ ಆಯ್ಕೆಯೊಂದಿಗೆ ನೀಡಲಾದ ಕುರುಹುಗಳ ಹೋಲಿಕೆಯು ಮರಣದಂಡನೆ ಪಥಗಳು ಬಹಳ ಮುಂಚೆಯೇ ಭಿನ್ನವಾಗಿದೆ ಎಂದು ತೋರಿಸಿದೆ. ಲಾಂಚರ್ ಬಳಸಿ ರೆಕಾರ್ಡ್ ಮಾಡಲಾದ ಹೋಲಿಕೆಯನ್ನು ಇಲ್ಲಿ ಹೇಳಬೇಕು emrun ಸ್ಥಳೀಯ ಜೋಡಣೆಯ ಔಟ್‌ಪುಟ್‌ನೊಂದಿಗೆ ಡೀಬಗ್ ಮಾಡುವ ಔಟ್‌ಪುಟ್ ಸಂಪೂರ್ಣವಾಗಿ ಯಾಂತ್ರಿಕ ಪ್ರಕ್ರಿಯೆಯಲ್ಲ. ಬ್ರೌಸರ್‌ನಲ್ಲಿ ಚಾಲನೆಯಲ್ಲಿರುವ ಪ್ರೋಗ್ರಾಂ ಹೇಗೆ ಸಂಪರ್ಕಿಸುತ್ತದೆ ಎಂದು ನನಗೆ ನಿಖರವಾಗಿ ತಿಳಿದಿಲ್ಲ emrun, ಆದರೆ ಔಟ್‌ಪುಟ್‌ನಲ್ಲಿನ ಕೆಲವು ಸಾಲುಗಳು ಮರುಜೋಡಣೆಯಾಗಿ ಹೊರಹೊಮ್ಮುತ್ತವೆ, ಆದ್ದರಿಂದ ವ್ಯತ್ಯಾಸದಲ್ಲಿನ ವ್ಯತ್ಯಾಸವು ಪಥಗಳು ಬೇರೆಡೆಗೆ ತಿರುಗಿವೆ ಎಂದು ಊಹಿಸಲು ಇನ್ನೂ ಒಂದು ಕಾರಣವಲ್ಲ. ಸಾಮಾನ್ಯವಾಗಿ, ಸೂಚನೆಗಳ ಪ್ರಕಾರ ಅದು ಸ್ಪಷ್ಟವಾಯಿತು ljmpl ವಿಭಿನ್ನ ವಿಳಾಸಗಳಿಗೆ ಪರಿವರ್ತನೆ ಇದೆ, ಮತ್ತು ರಚಿಸಲಾದ ಬೈಟ್‌ಕೋಡ್ ಮೂಲಭೂತವಾಗಿ ವಿಭಿನ್ನವಾಗಿದೆ: ಒಂದು ಸಹಾಯಕ ಕಾರ್ಯವನ್ನು ಕರೆಯುವ ಸೂಚನೆಯನ್ನು ಹೊಂದಿರುತ್ತದೆ, ಇನ್ನೊಂದು ಅಲ್ಲ. ಸೂಚನೆಗಳನ್ನು ಗೂಗ್ಲಿಂಗ್ ಮಾಡಿದ ನಂತರ ಮತ್ತು ಈ ಸೂಚನೆಗಳನ್ನು ಭಾಷಾಂತರಿಸುವ ಕೋಡ್ ಅನ್ನು ಅಧ್ಯಯನ ಮಾಡಿದ ನಂತರ, ಮೊದಲನೆಯದಾಗಿ, ರಿಜಿಸ್ಟರ್‌ನಲ್ಲಿ ತಕ್ಷಣವೇ ಮೊದಲು cr0 ರೆಕಾರ್ಡಿಂಗ್ ಅನ್ನು ಮಾಡಲಾಗಿದೆ - ಸಹಾಯಕವನ್ನು ಸಹ ಬಳಸಿ - ಇದು ಪ್ರೊಸೆಸರ್ ಅನ್ನು ಸಂರಕ್ಷಿತ ಮೋಡ್‌ಗೆ ಬದಲಾಯಿಸಿತು ಮತ್ತು ಎರಡನೆಯದಾಗಿ, js ಆವೃತ್ತಿಯು ಎಂದಿಗೂ ಸಂರಕ್ಷಿತ ಮೋಡ್‌ಗೆ ಬದಲಾಯಿಸಲಿಲ್ಲ. ಆದರೆ ವಾಸ್ತವವಾಗಿ ಎಂಸ್ಕ್ರಿಪ್ಟನ್‌ನ ಮತ್ತೊಂದು ವೈಶಿಷ್ಟ್ಯವೆಂದರೆ ಸೂಚನೆಗಳ ಅನುಷ್ಠಾನದಂತಹ ಕೋಡ್ ಅನ್ನು ಸಹಿಸಿಕೊಳ್ಳಲು ಇಷ್ಟವಿಲ್ಲದಿರುವುದು. call TCI ನಲ್ಲಿ, ಯಾವುದೇ ಫಂಕ್ಷನ್ ಪಾಯಿಂಟರ್ ಫಲಿತಾಂಶವನ್ನು ಟೈಪ್ ಮಾಡುತ್ತದೆ long long f(int arg0, .. int arg9) - ಕಾರ್ಯಗಳನ್ನು ಸರಿಯಾದ ಸಂಖ್ಯೆಯ ಆರ್ಗ್ಯುಮೆಂಟ್‌ಗಳೊಂದಿಗೆ ಕರೆಯಬೇಕು. ಈ ನಿಯಮವನ್ನು ಉಲ್ಲಂಘಿಸಿದರೆ, ಡೀಬಗ್ ಮಾಡುವ ಸೆಟ್ಟಿಂಗ್‌ಗಳನ್ನು ಅವಲಂಬಿಸಿ, ಪ್ರೋಗ್ರಾಂ ಕ್ರ್ಯಾಶ್ ಆಗುತ್ತದೆ (ಇದು ಒಳ್ಳೆಯದು) ಅಥವಾ ತಪ್ಪಾದ ಕಾರ್ಯವನ್ನು ಕರೆಯುತ್ತದೆ (ಇದು ಡೀಬಗ್ ಮಾಡಲು ದುಃಖವಾಗುತ್ತದೆ). ಮೂರನೆಯ ಆಯ್ಕೆಯೂ ಇದೆ - ಆರ್ಗ್ಯುಮೆಂಟ್‌ಗಳನ್ನು ಸೇರಿಸುವ / ತೆಗೆದುಹಾಕುವ ಹೊದಿಕೆಗಳ ಪೀಳಿಗೆಯನ್ನು ಸಕ್ರಿಯಗೊಳಿಸಿ, ಆದರೆ ಒಟ್ಟಾರೆಯಾಗಿ ಈ ಹೊದಿಕೆಗಳು ಸಾಕಷ್ಟು ಜಾಗವನ್ನು ತೆಗೆದುಕೊಳ್ಳುತ್ತವೆ, ವಾಸ್ತವವಾಗಿ ನನಗೆ ನೂರಕ್ಕೂ ಹೆಚ್ಚು ಹೊದಿಕೆಗಳು ಬೇಕಾಗುತ್ತವೆ. ಇದು ತುಂಬಾ ದುಃಖಕರವಾಗಿದೆ, ಆದರೆ ಹೆಚ್ಚು ಗಂಭೀರವಾದ ಸಮಸ್ಯೆ ಕಂಡುಬಂದಿದೆ: ಹೊದಿಕೆಯ ಕಾರ್ಯಗಳ ರಚಿತವಾದ ಕೋಡ್‌ನಲ್ಲಿ, ಆರ್ಗ್ಯುಮೆಂಟ್‌ಗಳನ್ನು ಪರಿವರ್ತಿಸಲಾಗುತ್ತದೆ ಮತ್ತು ಪರಿವರ್ತಿಸಲಾಗುತ್ತದೆ, ಆದರೆ ಕೆಲವೊಮ್ಮೆ ರಚಿತವಾದ ಆರ್ಗ್ಯುಮೆಂಟ್‌ಗಳೊಂದಿಗಿನ ಕಾರ್ಯವನ್ನು ಕರೆಯಲಾಗುವುದಿಲ್ಲ - ಅಲ್ಲದೆ, ಹಾಗೆ ನನ್ನ libffi ಅನುಷ್ಠಾನ. ಅಂದರೆ, ಕೆಲವು ಸಹಾಯಕರನ್ನು ಸರಳವಾಗಿ ಕಾರ್ಯಗತಗೊಳಿಸಲಾಗಿಲ್ಲ.

ಅದೃಷ್ಟವಶಾತ್, ಕ್ಯೂಮು ಹೆಡರ್ ಫೈಲ್‌ನ ರೂಪದಲ್ಲಿ ಸಹಾಯಕರ ಯಂತ್ರ-ಓದಬಲ್ಲ ಪಟ್ಟಿಗಳನ್ನು ಹೊಂದಿದೆ

DEF_HELPER_0(lock, void)
DEF_HELPER_0(unlock, void)
DEF_HELPER_3(write_eflags, void, env, tl, i32)

ಅವುಗಳನ್ನು ಸಾಕಷ್ಟು ತಮಾಷೆಯಾಗಿ ಬಳಸಲಾಗುತ್ತದೆ: ಮೊದಲನೆಯದಾಗಿ, ಮ್ಯಾಕ್ರೋಗಳನ್ನು ಅತ್ಯಂತ ವಿಲಕ್ಷಣ ರೀತಿಯಲ್ಲಿ ಮರು ವ್ಯಾಖ್ಯಾನಿಸಲಾಗಿದೆ DEF_HELPER_n, ಮತ್ತು ನಂತರ ಆನ್ ಆಗುತ್ತದೆ helper.h. ಮ್ಯಾಕ್ರೋವನ್ನು ರಚನೆಯ ಇನಿಶಿಯಲೈಜರ್ ಮತ್ತು ಅಲ್ಪವಿರಾಮವಾಗಿ ವಿಸ್ತರಿಸುವ ಮಟ್ಟಿಗೆ, ಮತ್ತು ನಂತರ ಒಂದು ಶ್ರೇಣಿಯನ್ನು ವ್ಯಾಖ್ಯಾನಿಸಲಾಗಿದೆ ಮತ್ತು ಅಂಶಗಳ ಬದಲಿಗೆ - #include <helper.h> ಪರಿಣಾಮವಾಗಿ, ನನಗೆ ಅಂತಿಮವಾಗಿ ಕೆಲಸದಲ್ಲಿ ಲೈಬ್ರರಿಯನ್ನು ಪ್ರಯತ್ನಿಸಲು ಅವಕಾಶ ಸಿಕ್ಕಿತು ಪೈಪಾರ್ಸಿಂಗ್, ಮತ್ತು ಸ್ಕ್ರಿಪ್ಟ್ ಅನ್ನು ಬರೆಯಲಾಗಿದೆ ಅದು ನಿಖರವಾಗಿ ಆ ಹೊದಿಕೆಗಳನ್ನು ಅವು ಅಗತ್ಯವಿರುವ ಕಾರ್ಯಗಳಿಗಾಗಿ ಉತ್ಪಾದಿಸುತ್ತದೆ.

ಮತ್ತು ಆದ್ದರಿಂದ, ಅದರ ನಂತರ ಪ್ರೊಸೆಸರ್ ಕೆಲಸ ತೋರುತ್ತಿದೆ. ಸ್ಥಳೀಯ ಅಸೆಂಬ್ಲಿಯಲ್ಲಿ memtest86+ ರನ್ ಮಾಡಲು ಸಾಧ್ಯವಾಗಿದ್ದರೂ, ಪರದೆಯನ್ನು ಎಂದಿಗೂ ಪ್ರಾರಂಭಿಸದ ಕಾರಣ ಇದು ತೋರುತ್ತದೆ. Qemu ಬ್ಲಾಕ್ I/O ಕೋಡ್ ಅನ್ನು ಕೊರೂಟಿನ್‌ಗಳಲ್ಲಿ ಬರೆಯಲಾಗಿದೆ ಎಂದು ಇಲ್ಲಿ ಸ್ಪಷ್ಟಪಡಿಸುವುದು ಅವಶ್ಯಕ. ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ತನ್ನದೇ ಆದ ಟ್ರಿಕಿ ಅಳವಡಿಕೆಯನ್ನು ಹೊಂದಿದೆ, ಆದರೆ ಅದನ್ನು ಇನ್ನೂ ಕ್ಯೂಮು ಕೋಡ್‌ನಲ್ಲಿ ಬೆಂಬಲಿಸುವ ಅಗತ್ಯವಿದೆ, ಮತ್ತು ನೀವು ಈಗ ಪ್ರೊಸೆಸರ್ ಅನ್ನು ಡೀಬಗ್ ಮಾಡಬಹುದು: ಕ್ಯೂಮು ಆಯ್ಕೆಗಳನ್ನು ಬೆಂಬಲಿಸುತ್ತದೆ -kernel, -initrd, -append, ಇದರೊಂದಿಗೆ ನೀವು Linux ಅನ್ನು ಬೂಟ್ ಮಾಡಬಹುದು ಅಥವಾ, ಉದಾಹರಣೆಗೆ, memtest86+, ಬ್ಲಾಕ್ ಸಾಧನಗಳನ್ನು ಬಳಸದೆಯೇ. ಆದರೆ ಇಲ್ಲಿ ಸಮಸ್ಯೆ ಇದೆ: ಸ್ಥಳೀಯ ಅಸೆಂಬ್ಲಿಯಲ್ಲಿ ಒಬ್ಬರು ಆಯ್ಕೆಯೊಂದಿಗೆ ಕನ್ಸೋಲ್‌ಗೆ ಲಿನಕ್ಸ್ ಕರ್ನಲ್ ಔಟ್‌ಪುಟ್ ಅನ್ನು ನೋಡಬಹುದು -nographic, ಮತ್ತು ಬ್ರೌಸರ್‌ನಿಂದ ಟರ್ಮಿನಲ್‌ಗೆ ಅದನ್ನು ಪ್ರಾರಂಭಿಸಿದ ಸ್ಥಳದಿಂದ ಯಾವುದೇ ಔಟ್‌ಪುಟ್ ಇಲ್ಲ emrun, ಬರಲಿಲ್ಲ. ಅಂದರೆ, ಇದು ಸ್ಪಷ್ಟವಾಗಿಲ್ಲ: ಪ್ರೊಸೆಸರ್ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತಿಲ್ಲ ಅಥವಾ ಗ್ರಾಫಿಕ್ಸ್ ಔಟ್ಪುಟ್ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತಿಲ್ಲ. ತದನಂತರ ಸ್ವಲ್ಪ ಕಾಯಬೇಕೆಂದು ನನಗೆ ಸಂಭವಿಸಿತು. "ಪ್ರೊಸೆಸರ್ ನಿದ್ರಿಸುತ್ತಿಲ್ಲ, ಆದರೆ ನಿಧಾನವಾಗಿ ಮಿಟುಕಿಸುತ್ತಿದೆ" ಎಂದು ಅದು ಬದಲಾಯಿತು ಮತ್ತು ಸುಮಾರು ಐದು ನಿಮಿಷಗಳ ನಂತರ ಕರ್ನಲ್ ಸಂದೇಶಗಳ ಗುಂಪನ್ನು ಕನ್ಸೋಲ್‌ಗೆ ಎಸೆದು ಸ್ಥಗಿತಗೊಳ್ಳುವುದನ್ನು ಮುಂದುವರೆಸಿತು. ಪ್ರೊಸೆಸರ್ ಸಾಮಾನ್ಯವಾಗಿ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತದೆ ಮತ್ತು SDL2 ನೊಂದಿಗೆ ಕೆಲಸ ಮಾಡಲು ನಾವು ಕೋಡ್ ಅನ್ನು ಡಿಗ್ ಮಾಡಬೇಕಾಗಿದೆ ಎಂಬುದು ಸ್ಪಷ್ಟವಾಯಿತು. ದುರದೃಷ್ಟವಶಾತ್, ಈ ಲೈಬ್ರರಿಯನ್ನು ಹೇಗೆ ಬಳಸಬೇಕೆಂದು ನನಗೆ ತಿಳಿದಿಲ್ಲ, ಆದ್ದರಿಂದ ಕೆಲವು ಸ್ಥಳಗಳಲ್ಲಿ ನಾನು ಯಾದೃಚ್ಛಿಕವಾಗಿ ವರ್ತಿಸಬೇಕಾಗಿತ್ತು. ಕೆಲವು ಹಂತದಲ್ಲಿ, ನೀಲಿ ಹಿನ್ನೆಲೆಯಲ್ಲಿ ಪರದೆಯ ಮೇಲೆ ಸಮಾನಾಂತರ 0 ಸಾಲು ಮಿನುಗಿತು, ಇದು ಕೆಲವು ಆಲೋಚನೆಗಳನ್ನು ಸೂಚಿಸಿತು. ಕೊನೆಯಲ್ಲಿ, ಸಮಸ್ಯೆಯೆಂದರೆ Qemu ಒಂದು ಭೌತಿಕ ವಿಂಡೋದಲ್ಲಿ ಹಲವಾರು ವರ್ಚುವಲ್ ವಿಂಡೋಗಳನ್ನು ತೆರೆಯುತ್ತದೆ, ಅದರ ನಡುವೆ ನೀವು Ctrl-Alt-n ಅನ್ನು ಬಳಸಿಕೊಂಡು ಬದಲಾಯಿಸಬಹುದು: ಇದು ಸ್ಥಳೀಯ ನಿರ್ಮಾಣದಲ್ಲಿ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತದೆ, ಆದರೆ Emscripten ನಲ್ಲಿ ಅಲ್ಲ. ಆಯ್ಕೆಗಳನ್ನು ಬಳಸಿಕೊಂಡು ಅನಗತ್ಯ ವಿಂಡೋಗಳನ್ನು ತೊಡೆದುಹಾಕಿದ ನಂತರ -monitor none -parallel none -serial none ಮತ್ತು ಪ್ರತಿ ಫ್ರೇಮ್‌ನಲ್ಲಿ ಸಂಪೂರ್ಣ ಪರದೆಯನ್ನು ಬಲವಂತವಾಗಿ ಪುನಃ ಚಿತ್ರಿಸಲು ಸೂಚನೆಗಳು, ಎಲ್ಲವೂ ಇದ್ದಕ್ಕಿದ್ದಂತೆ ಕೆಲಸ ಮಾಡುತ್ತವೆ.

ಕೊರೂಟಿನ್ಗಳು

ಆದ್ದರಿಂದ, ಬ್ರೌಸರ್ನಲ್ಲಿ ಎಮ್ಯುಲೇಶನ್ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತದೆ, ಆದರೆ ನೀವು ಅದರಲ್ಲಿ ಆಸಕ್ತಿದಾಯಕ ಸಿಂಗಲ್-ಫ್ಲಾಪಿ ಏನನ್ನೂ ಚಲಾಯಿಸಲು ಸಾಧ್ಯವಿಲ್ಲ, ಏಕೆಂದರೆ ಯಾವುದೇ ಬ್ಲಾಕ್ I / O ಇಲ್ಲ - ನೀವು ಕೊರೂಟಿನ್ಗಳಿಗೆ ಬೆಂಬಲವನ್ನು ಕಾರ್ಯಗತಗೊಳಿಸಬೇಕಾಗಿದೆ. Qemu ಈಗಾಗಲೇ ಹಲವಾರು ಕೊರೂಟಿನ್ ಬ್ಯಾಕೆಂಡ್‌ಗಳನ್ನು ಹೊಂದಿದೆ, ಆದರೆ ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್ ಮತ್ತು ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಕೋಡ್ ಜನರೇಟರ್‌ನ ಸ್ವಭಾವದಿಂದಾಗಿ, ನೀವು ಸ್ಟ್ಯಾಕ್‌ಗಳನ್ನು ಜಗ್ಲಿಂಗ್ ಮಾಡಲು ಪ್ರಾರಂಭಿಸಲು ಸಾಧ್ಯವಿಲ್ಲ. "ಎಲ್ಲವೂ ಹೋಗಿದೆ, ಪ್ಲ್ಯಾಸ್ಟರ್ ಅನ್ನು ತೆಗೆದುಹಾಕಲಾಗುತ್ತಿದೆ" ಎಂದು ತೋರುತ್ತದೆ, ಆದರೆ ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಡೆವಲಪರ್ಗಳು ಈಗಾಗಲೇ ಎಲ್ಲವನ್ನೂ ನೋಡಿಕೊಂಡಿದ್ದಾರೆ. ಇದನ್ನು ಸಾಕಷ್ಟು ತಮಾಷೆಯಾಗಿ ಅಳವಡಿಸಲಾಗಿದೆ: ಈ ರೀತಿಯ ಫಂಕ್ಷನ್ ಕರೆಯನ್ನು ಅನುಮಾನಾಸ್ಪದ ಎಂದು ಕರೆಯೋಣ emscripten_sleep ಮತ್ತು ಹಲವಾರು ಇತರರು Asyncify ಕಾರ್ಯವಿಧಾನವನ್ನು ಬಳಸುತ್ತಾರೆ, ಹಾಗೆಯೇ ಹಿಂದಿನ ಎರಡು ಪ್ರಕರಣಗಳಲ್ಲಿ ಒಂದನ್ನು ಸ್ಟಾಕ್‌ನ ಕೆಳಗೆ ಸಂಭವಿಸಬಹುದಾದ ಯಾವುದೇ ಕಾರ್ಯಕ್ಕೆ ಪಾಯಿಂಟರ್ ಕರೆಗಳು ಮತ್ತು ಕರೆಗಳು. ಮತ್ತು ಈಗ, ಪ್ರತಿ ಅನುಮಾನಾಸ್ಪದ ಕರೆಗೆ ಮೊದಲು, ನಾವು ಅಸಿಂಕ್ ಸಂದರ್ಭವನ್ನು ಆಯ್ಕೆ ಮಾಡುತ್ತೇವೆ ಮತ್ತು ಕರೆ ಮಾಡಿದ ತಕ್ಷಣ, ಅಸಮಕಾಲಿಕ ಕರೆ ಸಂಭವಿಸಿದೆಯೇ ಎಂದು ನಾವು ಪರಿಶೀಲಿಸುತ್ತೇವೆ ಮತ್ತು ಅದು ಹೊಂದಿದ್ದರೆ, ಈ ಅಸಿಂಕ್ ಸಂದರ್ಭದಲ್ಲಿ ನಾವು ಎಲ್ಲಾ ಸ್ಥಳೀಯ ಅಸ್ಥಿರಗಳನ್ನು ಉಳಿಸುತ್ತೇವೆ, ಯಾವ ಕಾರ್ಯವನ್ನು ಸೂಚಿಸುತ್ತೇವೆ ನಾವು ಎಕ್ಸಿಕ್ಯೂಶನ್ ಅನ್ನು ಮುಂದುವರಿಸಬೇಕಾದಾಗ ನಿಯಂತ್ರಣವನ್ನು ವರ್ಗಾಯಿಸಲು ಮತ್ತು ಪ್ರಸ್ತುತ ಕಾರ್ಯದಿಂದ ನಿರ್ಗಮಿಸಲು. ಇಲ್ಲಿಯೇ ಪರಿಣಾಮವನ್ನು ಅಧ್ಯಯನ ಮಾಡಲು ಅವಕಾಶವಿದೆ ದುಂದುವೆಚ್ಚ - ಅಸಮಕಾಲಿಕ ಕರೆಯಿಂದ ಹಿಂದಿರುಗಿದ ನಂತರ ಕೋಡ್ ಎಕ್ಸಿಕ್ಯೂಶನ್ ಅನ್ನು ಮುಂದುವರೆಸುವ ಅಗತ್ಯಗಳಿಗಾಗಿ, ಕಂಪೈಲರ್ ಕಾರ್ಯದ "ಸ್ಟಬ್‌ಗಳನ್ನು" ಉತ್ಪಾದಿಸುತ್ತದೆ, ಅನುಮಾನಾಸ್ಪದ ಕರೆ ನಂತರ ಪ್ರಾರಂಭವಾಗುತ್ತದೆ - ಈ ರೀತಿ: n ಅನುಮಾನಾಸ್ಪದ ಕರೆಗಳು ಇದ್ದರೆ, ನಂತರ ಕಾರ್ಯವನ್ನು ಎಲ್ಲೋ ವಿಸ್ತರಿಸಲಾಗುತ್ತದೆ n / 2 ಬಾರಿ - ಇದು ಇನ್ನೂ, ಇಲ್ಲದಿದ್ದರೆ ಪ್ರತಿ ಸಂಭಾವ್ಯ ಅಸಮಕಾಲಿಕ ಕರೆ ನಂತರ, ನೀವು ಮೂಲ ಕಾರ್ಯಕ್ಕೆ ಕೆಲವು ಸ್ಥಳೀಯ ಅಸ್ಥಿರಗಳನ್ನು ಉಳಿಸುವ ಅಗತ್ಯವಿದೆ ಎಂಬುದನ್ನು ನೆನಪಿನಲ್ಲಿಡಿ. ತರುವಾಯ, ನಾನು ಪೈಥಾನ್‌ನಲ್ಲಿ ಸರಳವಾದ ಸ್ಕ್ರಿಪ್ಟ್ ಅನ್ನು ಸಹ ಬರೆಯಬೇಕಾಗಿತ್ತು, ಇದು ನಿರ್ದಿಷ್ಟವಾಗಿ ಬಳಸಿದ ಕಾರ್ಯಗಳ ನಿರ್ದಿಷ್ಟ ಸೆಟ್ ಅನ್ನು ಆಧರಿಸಿ "ಅಸಿಂಕ್ರೊನಿಯನ್ನು ಸ್ವತಃ ಹಾದುಹೋಗಲು ಅನುಮತಿಸುವುದಿಲ್ಲ" (ಅಂದರೆ, ಸ್ಟಾಕ್ ಪ್ರಚಾರ ಮತ್ತು ನಾನು ವಿವರಿಸಿದ ಎಲ್ಲವೂ ಇಲ್ಲ ಅವುಗಳಲ್ಲಿ ಕೆಲಸ ಮಾಡಿ), ಪಾಯಿಂಟರ್‌ಗಳ ಮೂಲಕ ಕರೆಗಳನ್ನು ಸೂಚಿಸುತ್ತದೆ, ಇದರಲ್ಲಿ ಕಂಪೈಲರ್‌ನಿಂದ ಕಾರ್ಯಗಳನ್ನು ನಿರ್ಲಕ್ಷಿಸಬೇಕು ಆದ್ದರಿಂದ ಈ ಕಾರ್ಯಗಳನ್ನು ಅಸಮಕಾಲಿಕವೆಂದು ಪರಿಗಣಿಸಲಾಗುವುದಿಲ್ಲ. ತದನಂತರ 60 MB ಗಿಂತ ಕಡಿಮೆ ಇರುವ JS ಫೈಲ್‌ಗಳು ಸ್ಪಷ್ಟವಾಗಿ ತುಂಬಾ ಹೆಚ್ಚು - ಕನಿಷ್ಠ 30 ಎಂದು ಹೇಳೋಣ. ಆದರೂ, ಒಮ್ಮೆ ನಾನು ಅಸೆಂಬ್ಲಿ ಸ್ಕ್ರಿಪ್ಟ್ ಅನ್ನು ಹೊಂದಿಸುತ್ತಿದ್ದೆ ಮತ್ತು ಆಕಸ್ಮಿಕವಾಗಿ ಲಿಂಕರ್ ಆಯ್ಕೆಗಳನ್ನು ಎಸೆದಿದ್ದೇನೆ. -O3. ನಾನು ರಚಿಸಲಾದ ಕೋಡ್ ಅನ್ನು ರನ್ ಮಾಡುತ್ತೇನೆ ಮತ್ತು Chromium ಮೆಮೊರಿಯನ್ನು ತಿನ್ನುತ್ತದೆ ಮತ್ತು ಕ್ರ್ಯಾಶ್ ಆಗುತ್ತದೆ. ನಾನು ಆಕಸ್ಮಿಕವಾಗಿ ಅವನು ಡೌನ್‌ಲೋಡ್ ಮಾಡಲು ಪ್ರಯತ್ನಿಸುತ್ತಿರುವುದನ್ನು ನೋಡಿದೆ... ಸರಿ, ನಾನು ಏನು ಹೇಳಬಲ್ಲೆ, 500+ MB ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್ ಅನ್ನು ಚಿಂತನಶೀಲವಾಗಿ ಅಧ್ಯಯನ ಮಾಡಲು ಮತ್ತು ಆಪ್ಟಿಮೈಜ್ ಮಾಡಲು ನನ್ನನ್ನು ಕೇಳಿದ್ದರೆ ನಾನು ಕೂಡ ಫ್ರೀಜ್ ಆಗುತ್ತಿದ್ದೆ.

ದುರದೃಷ್ಟವಶಾತ್, Asyncify ಬೆಂಬಲ ಲೈಬ್ರರಿ ಕೋಡ್‌ನಲ್ಲಿನ ಚೆಕ್‌ಗಳು ಸಂಪೂರ್ಣವಾಗಿ ಸ್ನೇಹಪರವಾಗಿಲ್ಲ longjmp-s ಅನ್ನು ವರ್ಚುವಲ್ ಪ್ರೊಸೆಸರ್ ಕೋಡ್‌ನಲ್ಲಿ ಬಳಸಲಾಗುತ್ತದೆ, ಆದರೆ ಈ ಚೆಕ್‌ಗಳನ್ನು ನಿಷ್ಕ್ರಿಯಗೊಳಿಸುವ ಸಣ್ಣ ಪ್ಯಾಚ್‌ನ ನಂತರ ಮತ್ತು ಎಲ್ಲವೂ ಸರಿಯಾಗಿದೆ ಎಂಬಂತೆ ಸಂದರ್ಭಗಳನ್ನು ಬಲವಂತವಾಗಿ ಮರುಸ್ಥಾಪಿಸುತ್ತದೆ, ಕೋಡ್ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತದೆ. ತದನಂತರ ಒಂದು ವಿಚಿತ್ರ ವಿಷಯ ಪ್ರಾರಂಭವಾಯಿತು: ಕೆಲವೊಮ್ಮೆ ಸಿಂಕ್ರೊನೈಸೇಶನ್ ಕೋಡ್‌ನಲ್ಲಿನ ತಪಾಸಣೆಗಳನ್ನು ಪ್ರಚೋದಿಸಲಾಗುತ್ತದೆ - ಮರಣದಂಡನೆಯ ತರ್ಕದ ಪ್ರಕಾರ, ಅದನ್ನು ನಿರ್ಬಂಧಿಸಬೇಕಾದರೆ ಕೋಡ್ ಅನ್ನು ಕ್ರ್ಯಾಶ್ ಮಾಡುವ ಅದೇ ಪದಗಳು - ಯಾರಾದರೂ ಈಗಾಗಲೇ ಸೆರೆಹಿಡಿಯಲಾದ ಮ್ಯೂಟೆಕ್ಸ್ ಅನ್ನು ಪಡೆದುಕೊಳ್ಳಲು ಪ್ರಯತ್ನಿಸಿದರು. ಅದೃಷ್ಟವಶಾತ್, ಇದು ಧಾರಾವಾಹಿ ಕೋಡ್‌ನಲ್ಲಿ ತಾರ್ಕಿಕ ಸಮಸ್ಯೆಯಾಗಿಲ್ಲ - ನಾನು ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಒದಗಿಸಿದ ಪ್ರಮಾಣಿತ ಮುಖ್ಯ ಲೂಪ್ ಕಾರ್ಯವನ್ನು ಸರಳವಾಗಿ ಬಳಸುತ್ತಿದ್ದೆ, ಆದರೆ ಕೆಲವೊಮ್ಮೆ ಅಸಮಕಾಲಿಕ ಕರೆಯು ಸ್ಟಾಕ್ ಅನ್ನು ಸಂಪೂರ್ಣವಾಗಿ ಬಿಚ್ಚಿಡುತ್ತದೆ ಮತ್ತು ಆ ಕ್ಷಣದಲ್ಲಿ ಅದು ವಿಫಲಗೊಳ್ಳುತ್ತದೆ. setTimeout ಮುಖ್ಯ ಲೂಪ್‌ನಿಂದ - ಹೀಗಾಗಿ, ಹಿಂದಿನ ಪುನರಾವರ್ತನೆಯನ್ನು ಬಿಡದೆಯೇ ಕೋಡ್ ಮುಖ್ಯ ಲೂಪ್ ಪುನರಾವರ್ತನೆಯನ್ನು ಪ್ರವೇಶಿಸಿತು. ಅನಂತ ಲೂಪ್‌ನಲ್ಲಿ ಪುನಃ ಬರೆಯಲಾಗಿದೆ ಮತ್ತು emscripten_sleep, ಮತ್ತು ಮ್ಯೂಟೆಕ್ಸ್‌ಗಳೊಂದಿಗಿನ ಸಮಸ್ಯೆಗಳು ನಿಂತುಹೋದವು. ಕೋಡ್ ಇನ್ನಷ್ಟು ತಾರ್ಕಿಕವಾಗಿದೆ - ಎಲ್ಲಾ ನಂತರ, ಮುಂದಿನ ಅನಿಮೇಷನ್ ಫ್ರೇಮ್ ಅನ್ನು ಸಿದ್ಧಪಡಿಸುವ ಕೆಲವು ಕೋಡ್ ನನ್ನ ಬಳಿ ಇಲ್ಲ - ಪ್ರೊಸೆಸರ್ ಏನನ್ನಾದರೂ ಲೆಕ್ಕಾಚಾರ ಮಾಡುತ್ತದೆ ಮತ್ತು ಪರದೆಯನ್ನು ನಿಯತಕಾಲಿಕವಾಗಿ ನವೀಕರಿಸಲಾಗುತ್ತದೆ. ಆದಾಗ್ಯೂ, ಸಮಸ್ಯೆಗಳು ಅಲ್ಲಿ ನಿಲ್ಲಲಿಲ್ಲ: ಕೆಲವೊಮ್ಮೆ ಕ್ಯೂಮು ಮರಣದಂಡನೆಯು ಯಾವುದೇ ವಿನಾಯಿತಿಗಳು ಅಥವಾ ದೋಷಗಳಿಲ್ಲದೆ ಮೌನವಾಗಿ ಕೊನೆಗೊಳ್ಳುತ್ತದೆ. ಆ ಕ್ಷಣದಲ್ಲಿ ನಾನು ಅದನ್ನು ತ್ಯಜಿಸಿದೆ, ಆದರೆ, ಮುಂದೆ ನೋಡುವಾಗ, ಸಮಸ್ಯೆ ಇದು ಎಂದು ನಾನು ಹೇಳುತ್ತೇನೆ: ಕೊರೊಟಿನ್ ಕೋಡ್, ವಾಸ್ತವವಾಗಿ, ಬಳಸುವುದಿಲ್ಲ setTimeout (ಅಥವಾ ಕನಿಷ್ಠ ನೀವು ಯೋಚಿಸುವಷ್ಟು ಬಾರಿ ಅಲ್ಲ): ಕಾರ್ಯ emscripten_yield ಸರಳವಾಗಿ ಅಸಮಕಾಲಿಕ ಕರೆ ಫ್ಲ್ಯಾಗ್ ಅನ್ನು ಹೊಂದಿಸುತ್ತದೆ. ಸಂಪೂರ್ಣ ವಿಷಯವೆಂದರೆ ಅದು emscripten_coroutine_next ಅಸಮಕಾಲಿಕ ಕಾರ್ಯವಲ್ಲ: ಆಂತರಿಕವಾಗಿ ಇದು ಧ್ವಜವನ್ನು ಪರಿಶೀಲಿಸುತ್ತದೆ, ಅದನ್ನು ಮರುಹೊಂದಿಸುತ್ತದೆ ಮತ್ತು ಅಗತ್ಯವಿರುವ ಸ್ಥಳಕ್ಕೆ ನಿಯಂತ್ರಣವನ್ನು ವರ್ಗಾಯಿಸುತ್ತದೆ. ಅಂದರೆ, ಸ್ಟಾಕ್ನ ಪ್ರಚಾರವು ಅಲ್ಲಿಗೆ ಕೊನೆಗೊಳ್ಳುತ್ತದೆ. ಸಮಸ್ಯೆಯೆಂದರೆ, ಬಳಕೆಯ ನಂತರ-ಮುಕ್ತವಾಗಿ, ಕೊರೊಟಿನ್ ಪೂಲ್ ಅನ್ನು ನಿಷ್ಕ್ರಿಯಗೊಳಿಸಿದಾಗ ಕಾಣಿಸಿಕೊಂಡಿತು, ಏಕೆಂದರೆ ನಾನು ಅಸ್ತಿತ್ವದಲ್ಲಿರುವ ಕೊರೊಟಿನ್ ಬ್ಯಾಕೆಂಡ್, ಫಂಕ್ಷನ್‌ನಿಂದ ಕೋಡ್‌ನ ಪ್ರಮುಖ ಸಾಲನ್ನು ನಕಲಿಸಲಿಲ್ಲ qemu_in_coroutine ನಿಜವಾಗಿ ಅದು ಸುಳ್ಳನ್ನು ಹಿಂತಿರುಗಿಸಬೇಕಾದಾಗ ನಿಜವಾಗಿದೆ. ಇದು ಕರೆಗೆ ಕಾರಣವಾಯಿತು emscripten_yield, ಅದರ ಮೇಲೆ ಸ್ಟಾಕ್‌ನಲ್ಲಿ ಯಾರೂ ಇರಲಿಲ್ಲ emscripten_coroutine_next, ಸ್ಟಾಕ್ ಅತ್ಯಂತ ಮೇಲಕ್ಕೆ ತೆರೆದುಕೊಂಡಿತು, ಆದರೆ ಇಲ್ಲ setTimeout, ನಾನು ಈಗಾಗಲೇ ಹೇಳಿದಂತೆ, ಪ್ರದರ್ಶಿಸಲಾಗಿಲ್ಲ.

ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್ ಕೋಡ್ ಉತ್ಪಾದನೆ

ಮತ್ತು ಇಲ್ಲಿ, ವಾಸ್ತವವಾಗಿ, "ಕೊಚ್ಚಿದ ಮಾಂಸವನ್ನು ಹಿಂದಕ್ಕೆ ತಿರುಗಿಸುವ" ಭರವಸೆ ಇದೆ. ನಿಜವಾಗಿಯೂ ಅಲ್ಲ. ಸಹಜವಾಗಿ, ನಾವು ಬ್ರೌಸರ್‌ನಲ್ಲಿ Qemu ಅನ್ನು ಚಲಾಯಿಸಿದರೆ ಮತ್ತು ಅದರಲ್ಲಿ Node.js ಅನ್ನು ಚಲಾಯಿಸಿದರೆ, ಸ್ವಾಭಾವಿಕವಾಗಿ, Qemu ನಲ್ಲಿ ಕೋಡ್ ಉತ್ಪಾದನೆಯ ನಂತರ ನಾವು ಸಂಪೂರ್ಣವಾಗಿ ತಪ್ಪು JavaScript ಅನ್ನು ಪಡೆಯುತ್ತೇವೆ. ಆದರೆ ಇನ್ನೂ, ಕೆಲವು ರೀತಿಯ ರಿವರ್ಸ್ ರೂಪಾಂತರ.

ಮೊದಲಿಗೆ, ಕ್ಯೂಮು ಹೇಗೆ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತದೆ ಎಂಬುದರ ಕುರಿತು ಸ್ವಲ್ಪ. ದಯವಿಟ್ಟು ಈಗಿನಿಂದಲೇ ನನ್ನನ್ನು ಕ್ಷಮಿಸಿ: ನಾನು ವೃತ್ತಿಪರ Qemu ಡೆವಲಪರ್ ಅಲ್ಲ ಮತ್ತು ನನ್ನ ತೀರ್ಮಾನಗಳು ಕೆಲವು ಸ್ಥಳಗಳಲ್ಲಿ ತಪ್ಪಾಗಿರಬಹುದು. ಅವರು ಹೇಳಿದಂತೆ, "ವಿದ್ಯಾರ್ಥಿಯ ಅಭಿಪ್ರಾಯವು ಶಿಕ್ಷಕರ ಅಭಿಪ್ರಾಯ, ಪೀನೋ ಅವರ ಆಕ್ಸಿಯೋಮ್ಯಾಟಿಕ್ಸ್ ಮತ್ತು ಸಾಮಾನ್ಯ ಜ್ಞಾನದೊಂದಿಗೆ ಹೊಂದಿಕೆಯಾಗಬೇಕಾಗಿಲ್ಲ." Qemu ನಿರ್ದಿಷ್ಟ ಸಂಖ್ಯೆಯ ಬೆಂಬಲಿತ ಅತಿಥಿ ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗಳನ್ನು ಹೊಂದಿದೆ ಮತ್ತು ಪ್ರತಿಯೊಂದಕ್ಕೂ ಒಂದು ಡೈರೆಕ್ಟರಿ ಇರುತ್ತದೆ target-i386. ನಿರ್ಮಿಸುವಾಗ, ನೀವು ಹಲವಾರು ಅತಿಥಿ ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗಳಿಗೆ ಬೆಂಬಲವನ್ನು ಸೂಚಿಸಬಹುದು, ಆದರೆ ಫಲಿತಾಂಶವು ಕೇವಲ ಹಲವಾರು ಬೈನರಿಗಳಾಗಿರುತ್ತದೆ. ಅತಿಥಿ ಆರ್ಕಿಟೆಕ್ಚರ್ ಅನ್ನು ಬೆಂಬಲಿಸುವ ಕೋಡ್, ಪ್ರತಿಯಾಗಿ, ಕೆಲವು ಆಂತರಿಕ ಕ್ಯೂಮು ಕಾರ್ಯಾಚರಣೆಗಳನ್ನು ಉತ್ಪಾದಿಸುತ್ತದೆ, ಇದು TCG (ಸಣ್ಣ ಕೋಡ್ ಜನರೇಟರ್) ಈಗಾಗಲೇ ಹೋಸ್ಟ್ ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗಾಗಿ ಯಂತ್ರ ಸಂಕೇತವಾಗಿ ಬದಲಾಗುತ್ತದೆ. tcg ಡೈರೆಕ್ಟರಿಯಲ್ಲಿರುವ readme ಫೈಲ್‌ನಲ್ಲಿ ಹೇಳಿರುವಂತೆ, ಇದು ಮೂಲತಃ ಸಾಮಾನ್ಯ C ಕಂಪೈಲರ್‌ನ ಭಾಗವಾಗಿತ್ತು, ಇದನ್ನು ನಂತರ JIT ಗಾಗಿ ಅಳವಡಿಸಲಾಯಿತು. ಆದ್ದರಿಂದ, ಉದಾಹರಣೆಗೆ, ಈ ಡಾಕ್ಯುಮೆಂಟ್‌ನ ವಿಷಯದಲ್ಲಿ ಟಾರ್ಗೆಟ್ ಆರ್ಕಿಟೆಕ್ಚರ್ ಇನ್ನು ಮುಂದೆ ಅತಿಥಿ ಆರ್ಕಿಟೆಕ್ಚರ್ ಆಗಿರುವುದಿಲ್ಲ, ಆದರೆ ಹೋಸ್ಟ್ ಆರ್ಕಿಟೆಕ್ಚರ್ ಆಗಿದೆ. ಕೆಲವು ಹಂತದಲ್ಲಿ, ಮತ್ತೊಂದು ಘಟಕವು ಕಾಣಿಸಿಕೊಂಡಿತು - ಟೈನಿ ಕೋಡ್ ಇಂಟರ್ಪ್ರಿಟರ್ (ಟಿಸಿಐ), ನಿರ್ದಿಷ್ಟ ಹೋಸ್ಟ್ ಆರ್ಕಿಟೆಕ್ಚರ್ಗಾಗಿ ಕೋಡ್ ಜನರೇಟರ್ ಅನುಪಸ್ಥಿತಿಯಲ್ಲಿ ಕೋಡ್ ಅನ್ನು (ಬಹುತೇಕ ಅದೇ ಆಂತರಿಕ ಕಾರ್ಯಾಚರಣೆಗಳು) ಕಾರ್ಯಗತಗೊಳಿಸಬೇಕು. ವಾಸ್ತವವಾಗಿ, ಅದರ ದಸ್ತಾವೇಜನ್ನು ಹೇಳುವಂತೆ, ಈ ಇಂಟರ್ಪ್ರಿಟರ್ ಯಾವಾಗಲೂ JIT ಕೋಡ್ ಜನರೇಟರ್ನಂತೆ ಕಾರ್ಯನಿರ್ವಹಿಸುವುದಿಲ್ಲ, ವೇಗದ ವಿಷಯದಲ್ಲಿ ಪರಿಮಾಣಾತ್ಮಕವಾಗಿ ಮಾತ್ರವಲ್ಲದೆ ಗುಣಾತ್ಮಕವಾಗಿಯೂ ಸಹ. ಅವರ ವಿವರಣೆಯು ಸಂಪೂರ್ಣವಾಗಿ ಪ್ರಸ್ತುತವಾಗಿದೆ ಎಂದು ನನಗೆ ಖಚಿತವಾಗಿಲ್ಲವಾದರೂ.

ಮೊದಲಿಗೆ ನಾನು ಪೂರ್ಣ ಪ್ರಮಾಣದ TCG ಬ್ಯಾಕೆಂಡ್ ಮಾಡಲು ಪ್ರಯತ್ನಿಸಿದೆ, ಆದರೆ ಮೂಲ ಕೋಡ್‌ನಲ್ಲಿ ತ್ವರಿತವಾಗಿ ಗೊಂದಲಕ್ಕೊಳಗಾಯಿತು ಮತ್ತು ಬೈಟ್‌ಕೋಡ್ ಸೂಚನೆಗಳ ಸಂಪೂರ್ಣ ಸ್ಪಷ್ಟ ವಿವರಣೆಯಿಲ್ಲ, ಆದ್ದರಿಂದ ನಾನು TCI ಇಂಟರ್ಪ್ರಿಟರ್ ಅನ್ನು ಕಟ್ಟಲು ನಿರ್ಧರಿಸಿದೆ. ಇದು ಹಲವಾರು ಪ್ರಯೋಜನಗಳನ್ನು ನೀಡಿತು:

  • ಕೋಡ್ ಜನರೇಟರ್ ಅನ್ನು ಕಾರ್ಯಗತಗೊಳಿಸುವಾಗ, ನೀವು ಸೂಚನೆಗಳ ವಿವರಣೆಯನ್ನು ನೋಡಬಾರದು, ಆದರೆ ಇಂಟರ್ಪ್ರಿಟರ್ ಕೋಡ್ ಅನ್ನು ನೋಡಬಹುದು
  • ನೀವು ಎದುರಿಸಿದ ಪ್ರತಿ ಅನುವಾದ ಬ್ಲಾಕ್‌ಗೆ ಅಲ್ಲ, ಆದರೆ, ಉದಾಹರಣೆಗೆ, ನೂರನೇ ಕಾರ್ಯಗತಗೊಳಿಸಿದ ನಂತರ ಮಾತ್ರ ನೀವು ಕಾರ್ಯಗಳನ್ನು ರಚಿಸಬಹುದು
  • ರಚಿತವಾದ ಕೋಡ್ ಬದಲಾದರೆ (ಮತ್ತು ಇದು ಸಾಧ್ಯವಾಗುವಂತೆ ತೋರುತ್ತಿದೆ, ಪ್ಯಾಚ್ ಪದವನ್ನು ಹೊಂದಿರುವ ಹೆಸರುಗಳೊಂದಿಗೆ ಕಾರ್ಯಗಳ ಮೂಲಕ ನಿರ್ಣಯಿಸುವುದು), ನಾನು ರಚಿಸಿದ JS ಕೋಡ್ ಅನ್ನು ಅಮಾನ್ಯಗೊಳಿಸಬೇಕಾಗಿದೆ, ಆದರೆ ಕನಿಷ್ಠ ಅದನ್ನು ಪುನರುತ್ಪಾದಿಸಲು ನಾನು ಏನನ್ನಾದರೂ ಹೊಂದಿರುತ್ತೇನೆ.

ಮೂರನೇ ಅಂಶಕ್ಕೆ ಸಂಬಂಧಿಸಿದಂತೆ, ಕೋಡ್ ಅನ್ನು ಮೊದಲ ಬಾರಿಗೆ ಕಾರ್ಯಗತಗೊಳಿಸಿದ ನಂತರ ಪ್ಯಾಚಿಂಗ್ ಸಾಧ್ಯ ಎಂದು ನನಗೆ ಖಚಿತವಿಲ್ಲ, ಆದರೆ ಮೊದಲ ಎರಡು ಅಂಕಗಳು ಸಾಕು.

ಆರಂಭದಲ್ಲಿ, ಕೋಡ್ ಅನ್ನು ಮೂಲ ಬೈಟ್‌ಕೋಡ್ ಸೂಚನೆಯ ವಿಳಾಸದಲ್ಲಿ ದೊಡ್ಡ ಸ್ವಿಚ್ ರೂಪದಲ್ಲಿ ರಚಿಸಲಾಯಿತು, ಆದರೆ ನಂತರ, ಎಂಸ್ಕ್ರಿಪ್ಟನ್, ರಚಿತವಾದ JS ನ ಆಪ್ಟಿಮೈಸೇಶನ್ ಮತ್ತು ರೀಲೂಪಿಂಗ್ ಕುರಿತು ಲೇಖನವನ್ನು ನೆನಪಿಸಿಕೊಂಡು, ನಾನು ಹೆಚ್ಚು ಮಾನವ ಕೋಡ್ ಅನ್ನು ರಚಿಸಲು ನಿರ್ಧರಿಸಿದೆ, ವಿಶೇಷವಾಗಿ ಪ್ರಾಯೋಗಿಕವಾಗಿ ಅದು ಅನುವಾದ ಬ್ಲಾಕ್‌ಗೆ ಪ್ರವೇಶ ಬಿಂದುವು ಅದರ ಪ್ರಾರಂಭವಾಗಿದೆ ಎಂದು ಬದಲಾಯಿತು. ಸ್ವಲ್ಪ ಸಮಯದ ನಂತರ ನಾವು ಕೋಡ್ ಜನರೇಟರ್ ಹೊಂದಿದ್ದೇವೆ, ಅದು ಐಎಫ್‌ಎಸ್‌ನೊಂದಿಗೆ ಕೋಡ್ ಅನ್ನು ರಚಿಸಿದೆ (ಲೂಪ್‌ಗಳಿಲ್ಲದಿದ್ದರೂ). ಆದರೆ ದುರಾದೃಷ್ಟ, ಅದು ಅಪ್ಪಳಿಸಿತು, ಸೂಚನೆಗಳು ಕೆಲವು ತಪ್ಪಾದ ಉದ್ದವನ್ನು ಹೊಂದಿವೆ ಎಂಬ ಸಂದೇಶವನ್ನು ನೀಡಿತು. ಇದಲ್ಲದೆ, ಈ ಪುನರಾವರ್ತನೆಯ ಮಟ್ಟದಲ್ಲಿ ಕೊನೆಯ ಸೂಚನೆಯಾಗಿತ್ತು brcond. ಸರಿ, ನಾನು ಪುನರಾವರ್ತಿತ ಕರೆಗೆ ಮೊದಲು ಮತ್ತು ನಂತರ ಈ ಸೂಚನೆಯ ಪೀಳಿಗೆಗೆ ಒಂದೇ ರೀತಿಯ ಚೆಕ್ ಅನ್ನು ಸೇರಿಸುತ್ತೇನೆ ಮತ್ತು... ಅವುಗಳಲ್ಲಿ ಒಂದನ್ನು ಕಾರ್ಯಗತಗೊಳಿಸಲಾಗಿಲ್ಲ, ಆದರೆ ಪ್ರತಿಪಾದನೆಯ ಸ್ವಿಚ್ ನಂತರ ಅವು ಇನ್ನೂ ವಿಫಲವಾಗಿವೆ. ಕೊನೆಯಲ್ಲಿ, ರಚಿಸಿದ ಕೋಡ್ ಅನ್ನು ಅಧ್ಯಯನ ಮಾಡಿದ ನಂತರ, ಸ್ವಿಚ್ ನಂತರ, ಪ್ರಸ್ತುತ ಸೂಚನೆಗೆ ಪಾಯಿಂಟರ್ ಅನ್ನು ಸ್ಟಾಕ್‌ನಿಂದ ಮರುಲೋಡ್ ಮಾಡಲಾಗಿದೆ ಮತ್ತು ಬಹುಶಃ ರಚಿತವಾದ ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್ ಕೋಡ್‌ನಿಂದ ತಿದ್ದಿ ಬರೆಯಲಾಗುತ್ತದೆ ಎಂದು ನಾನು ಅರಿತುಕೊಂಡೆ. ಮತ್ತು ಆದ್ದರಿಂದ ಅದು ಬದಲಾಯಿತು. ಬಫರ್ ಅನ್ನು ಒಂದು ಮೆಗಾಬೈಟ್‌ನಿಂದ ಹತ್ತಕ್ಕೆ ಹೆಚ್ಚಿಸುವುದರಿಂದ ಯಾವುದಕ್ಕೂ ಕಾರಣವಾಗಲಿಲ್ಲ ಮತ್ತು ಕೋಡ್ ಜನರೇಟರ್ ವಲಯಗಳಲ್ಲಿ ಚಾಲನೆಯಲ್ಲಿದೆ ಎಂಬುದು ಸ್ಪಷ್ಟವಾಯಿತು. ನಾವು ಪ್ರಸ್ತುತ TB ಯ ಗಡಿಗಳನ್ನು ಮೀರಿ ಹೋಗಿಲ್ಲ ಎಂದು ನಾವು ಪರಿಶೀಲಿಸಬೇಕಾಗಿತ್ತು ಮತ್ತು ನಾವು ಮಾಡಿದರೆ, ಮುಂದಿನ TB ಯ ವಿಳಾಸವನ್ನು ಮೈನಸ್ ಚಿಹ್ನೆಯೊಂದಿಗೆ ನೀಡಿ ಇದರಿಂದ ನಾವು ಮರಣದಂಡನೆಯನ್ನು ಮುಂದುವರಿಸಬಹುದು. ಹೆಚ್ಚುವರಿಯಾಗಿ, "ಈ ಬೈಟ್‌ಕೋಡ್‌ನ ತುಣುಕು ಬದಲಾಗಿದ್ದರೆ ಯಾವ ರಚಿತ ಕಾರ್ಯಗಳನ್ನು ಅಮಾನ್ಯಗೊಳಿಸಬೇಕು?" ಎಂಬ ಸಮಸ್ಯೆಯನ್ನು ಇದು ಪರಿಹರಿಸುತ್ತದೆ. — ಈ ಅನುವಾದ ಬ್ಲಾಕ್‌ಗೆ ಅನುಗುಣವಾದ ಕಾರ್ಯವನ್ನು ಮಾತ್ರ ಅಮಾನ್ಯಗೊಳಿಸಬೇಕಾಗಿದೆ. ಅಂದಹಾಗೆ, ನಾನು ಕ್ರೋಮಿಯಂನಲ್ಲಿ ಎಲ್ಲವನ್ನೂ ಡೀಬಗ್ ಮಾಡಿದ್ದರೂ (ನಾನು ಫೈರ್‌ಫಾಕ್ಸ್ ಅನ್ನು ಬಳಸುವುದರಿಂದ ಮತ್ತು ಪ್ರಯೋಗಗಳಿಗಾಗಿ ಪ್ರತ್ಯೇಕ ಬ್ರೌಸರ್ ಅನ್ನು ಬಳಸಲು ನನಗೆ ಸುಲಭವಾಗಿದೆ), ಫೈರ್‌ಫಾಕ್ಸ್ ನನಗೆ asm.js ಮಾನದಂಡದೊಂದಿಗೆ ಅಸಾಮರಸ್ಯವನ್ನು ಸರಿಪಡಿಸಲು ಸಹಾಯ ಮಾಡಿತು, ಅದರ ನಂತರ ಕೋಡ್ ವೇಗವಾಗಿ ಕೆಲಸ ಮಾಡಲು ಪ್ರಾರಂಭಿಸಿತು. ಕ್ರೋಮಿಯಂ.

ರಚಿಸಿದ ಕೋಡ್‌ನ ಉದಾಹರಣೆ

Compiling 0x15b46d0:
CompiledTB[0x015b46d0] = function(stdlib, ffi, heap) {
"use asm";
var HEAP8 = new stdlib.Int8Array(heap);
var HEAP16 = new stdlib.Int16Array(heap);
var HEAP32 = new stdlib.Int32Array(heap);
var HEAPU8 = new stdlib.Uint8Array(heap);
var HEAPU16 = new stdlib.Uint16Array(heap);
var HEAPU32 = new stdlib.Uint32Array(heap);

var dynCall_iiiiiiiiiii = ffi.dynCall_iiiiiiiiiii;
var getTempRet0 = ffi.getTempRet0;
var badAlignment = ffi.badAlignment;
var _i64Add = ffi._i64Add;
var _i64Subtract = ffi._i64Subtract;
var Math_imul = ffi.Math_imul;
var _mul_unsigned_long_long = ffi._mul_unsigned_long_long;
var execute_if_compiled = ffi.execute_if_compiled;
var getThrew = ffi.getThrew;
var abort = ffi.abort;
var qemu_ld_ub = ffi.qemu_ld_ub;
var qemu_ld_leuw = ffi.qemu_ld_leuw;
var qemu_ld_leul = ffi.qemu_ld_leul;
var qemu_ld_beuw = ffi.qemu_ld_beuw;
var qemu_ld_beul = ffi.qemu_ld_beul;
var qemu_ld_beq = ffi.qemu_ld_beq;
var qemu_ld_leq = ffi.qemu_ld_leq;
var qemu_st_b = ffi.qemu_st_b;
var qemu_st_lew = ffi.qemu_st_lew;
var qemu_st_lel = ffi.qemu_st_lel;
var qemu_st_bew = ffi.qemu_st_bew;
var qemu_st_bel = ffi.qemu_st_bel;
var qemu_st_leq = ffi.qemu_st_leq;
var qemu_st_beq = ffi.qemu_st_beq;

function tb_fun(tb_ptr, env, sp_value, depth) {
  tb_ptr = tb_ptr|0;
  env = env|0;
  sp_value = sp_value|0;
  depth = depth|0;
  var u0 = 0, u1 = 0, u2 = 0, u3 = 0, result = 0;
  var r0 = 0, r1 = 0, r2 = 0, r3 = 0, r4 = 0, r5 = 0, r6 = 0, r7 = 0, r8 = 0, r9 = 0;
  var r10 = 0, r11 = 0, r12 = 0, r13 = 0, r14 = 0, r15 = 0, r16 = 0, r17 = 0, r18 = 0, r19 = 0;
  var r20 = 0, r21 = 0, r22 = 0, r23 = 0, r24 = 0, r25 = 0, r26 = 0, r27 = 0, r28 = 0, r29 = 0;
  var r30 = 0, r31 = 0, r41 = 0, r42 = 0, r43 = 0, r44 = 0;
    r14 = env|0;
    r15 = sp_value|0;
  START: do {
    r0 = HEAPU32[((r14 + (-4))|0) >> 2] | 0;
    r42 = 0;
    result = ((r0|0) != (r42|0))|0;
    HEAPU32[1445307] = r0;
    HEAPU32[1445321] = r14;
    if(result|0) {
    HEAPU32[1445322] = r15;
    return 0x0345bf93|0;
    }
    r0 = HEAPU32[((r14 + (16))|0) >> 2] | 0;
    r42 = 8;
    r0 = ((r0|0) - (r42|0))|0;
    HEAPU32[(r14 + (16)) >> 2] = r0;
    r1 = 8;
    HEAPU32[(r14 + (44)) >> 2] = r1;
    r1 = r0|0;
    HEAPU32[(r14 + (40)) >> 2] = r1;
    r42 = 4;
    r0 = ((r0|0) + (r42|0))|0;
    r2 = HEAPU32[((r14 + (24))|0) >> 2] | 0;
    HEAPU32[1445307] = r0;
    HEAPU32[1445308] = r1;
    HEAPU32[1445309] = r2;
    HEAPU32[1445321] = r14;
    HEAPU32[1445322] = r15;
    qemu_st_lel(env|0, r0|0, r2|0, 34, 22759218);
if(getThrew() | 0) abort();
    r0 = 3241038392;
    HEAPU32[1445307] = r0;
    r0 = qemu_ld_leul(env|0, r0|0, 34, 22759233)|0;
if(getThrew() | 0) abort();
    HEAPU32[(r14 + (24)) >> 2] = r0;
    r1 = HEAPU32[((r14 + (12))|0) >> 2] | 0;
    r2 = HEAPU32[((r14 + (40))|0) >> 2] | 0;
    HEAPU32[1445307] = r0;
    HEAPU32[1445308] = r1;
    HEAPU32[1445309] = r2;
    qemu_st_lel(env|0, r2|0, r1|0, 34, 22759265);
if(getThrew() | 0) abort();
    r0 = HEAPU32[((r14 + (24))|0) >> 2] | 0;
    HEAPU32[(r14 + (40)) >> 2] = r0;
    r1 = 24;
    HEAPU32[(r14 + (52)) >> 2] = r1;
    r42 = 0;
    result = ((r0|0) == (r42|0))|0;
    if(result|0) {
    HEAPU32[1445307] = r0;
    HEAPU32[1445308] = r1;
    }
    HEAPU32[1445307] = r0;
    HEAPU32[1445308] = r1;
    return execute_if_compiled(22759392|0, env|0, sp_value|0, depth|0) | 0;
    return execute_if_compiled(23164080|0, env|0, sp_value|0, depth|0) | 0;
    break;
  } while(1); abort(); return 0|0;
}
return {tb_fun: tb_fun};
}(window, CompilerFFI, Module.buffer)["tb_fun"]

ತೀರ್ಮಾನಕ್ಕೆ

ಆದ್ದರಿಂದ, ಕೆಲಸವು ಇನ್ನೂ ಪೂರ್ಣಗೊಂಡಿಲ್ಲ, ಆದರೆ ಈ ದೀರ್ಘಾವಧಿಯ ನಿರ್ಮಾಣವನ್ನು ರಹಸ್ಯವಾಗಿ ಪರಿಪೂರ್ಣತೆಗೆ ತರುವಲ್ಲಿ ನಾನು ಆಯಾಸಗೊಂಡಿದ್ದೇನೆ. ಆದ್ದರಿಂದ, ಸದ್ಯಕ್ಕೆ ನನ್ನಲ್ಲಿರುವದನ್ನು ಪ್ರಕಟಿಸಲು ನಾನು ನಿರ್ಧರಿಸಿದೆ. ಕೋಡ್ ಸ್ಥಳಗಳಲ್ಲಿ ಸ್ವಲ್ಪ ಭಯಾನಕವಾಗಿದೆ, ಏಕೆಂದರೆ ಇದು ಪ್ರಯೋಗವಾಗಿದೆ, ಮತ್ತು ಏನು ಮಾಡಬೇಕೆಂದು ಮುಂಚಿತವಾಗಿ ಸ್ಪಷ್ಟವಾಗಿಲ್ಲ. ಬಹುಶಃ, Qemu ನ ಕೆಲವು ಆಧುನಿಕ ಆವೃತ್ತಿಯ ಮೇಲೆ ಸಾಮಾನ್ಯ ಪರಮಾಣು ಕಮಿಟ್‌ಗಳನ್ನು ನೀಡುವುದು ಯೋಗ್ಯವಾಗಿದೆ. ಈ ಮಧ್ಯೆ, ಬ್ಲಾಗ್ ಸ್ವರೂಪದಲ್ಲಿ ಗೀತಾದಲ್ಲಿ ಒಂದು ಥ್ರೆಡ್ ಇದೆ: ಕನಿಷ್ಠ ಹೇಗಾದರೂ ಅಂಗೀಕರಿಸಲ್ಪಟ್ಟ ಪ್ರತಿ "ಮಟ್ಟ" ಕ್ಕೆ, ರಷ್ಯನ್ ಭಾಷೆಯಲ್ಲಿ ವಿವರವಾದ ವ್ಯಾಖ್ಯಾನವನ್ನು ಸೇರಿಸಲಾಗಿದೆ. ವಾಸ್ತವವಾಗಿ, ಈ ಲೇಖನವು ಹೆಚ್ಚಿನ ಮಟ್ಟಿಗೆ ತೀರ್ಮಾನದ ಪುನರಾವರ್ತನೆಯಾಗಿದೆ git log.

ನೀವು ಎಲ್ಲವನ್ನೂ ಪ್ರಯತ್ನಿಸಬಹುದು ಇಲ್ಲಿ (ಸಂಚಾರದ ಬಗ್ಗೆ ಎಚ್ಚರದಿಂದಿರಿ).

ಈಗಾಗಲೇ ಏನು ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತಿದೆ:

  • x86 ವರ್ಚುವಲ್ ಪ್ರೊಸೆಸರ್ ಚಾಲನೆಯಲ್ಲಿದೆ
  • ಯಂತ್ರ ಕೋಡ್‌ನಿಂದ ಜಾವಾಸ್ಕ್ರಿಪ್ಟ್‌ಗೆ JIT ಕೋಡ್ ಜನರೇಟರ್‌ನ ಕೆಲಸದ ಮೂಲಮಾದರಿ ಇದೆ
  • ಇತರ 32-ಬಿಟ್ ಅತಿಥಿ ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗಳನ್ನು ಜೋಡಿಸಲು ಒಂದು ಟೆಂಪ್ಲೇಟ್ ಇದೆ: ಇದೀಗ ನೀವು ಲೋಡಿಂಗ್ ಹಂತದಲ್ಲಿ ಬ್ರೌಸರ್‌ನಲ್ಲಿ ಫ್ರೀಜ್ ಮಾಡುವ MIPS ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗಾಗಿ Linux ಅನ್ನು ಮೆಚ್ಚಬಹುದು

ಇನ್ನೇನು ಮಾಡಬಹುದು

  • ಎಮ್ಯುಲೇಶನ್ ಅನ್ನು ವೇಗಗೊಳಿಸಿ. JIT ಮೋಡ್‌ನಲ್ಲಿಯೂ ಸಹ ಇದು ವರ್ಚುವಲ್ x86 ಗಿಂತ ನಿಧಾನವಾಗಿ ಕಾರ್ಯನಿರ್ವಹಿಸುತ್ತದೆ ಎಂದು ತೋರುತ್ತದೆ (ಆದರೆ ಸಾಕಷ್ಟು ಎಮ್ಯುಲೇಟೆಡ್ ಹಾರ್ಡ್‌ವೇರ್ ಮತ್ತು ಆರ್ಕಿಟೆಕ್ಚರ್‌ಗಳೊಂದಿಗೆ ಸಂಪೂರ್ಣ ಕ್ಯೂಮು ಇದೆ)
  • ಸಾಮಾನ್ಯ ಇಂಟರ್ಫೇಸ್ ಮಾಡಲು - ನಾನೂ ಉತ್ತಮ ವೆಬ್ ಡೆವಲಪರ್ ಅಲ್ಲ, ಹಾಗಾಗಿ ಸದ್ಯಕ್ಕೆ ನಾನು ಸ್ಟ್ಯಾಂಡರ್ಡ್ ಎಂಸ್ಕ್ರಿಪ್ಟನ್ ಶೆಲ್ ಅನ್ನು ನನ್ನ ಕೈಲಾದಷ್ಟು ರಿಮೇಕ್ ಮಾಡಿದ್ದೇನೆ
  • ಹೆಚ್ಚು ಸಂಕೀರ್ಣವಾದ Qemu ಕಾರ್ಯಗಳನ್ನು ಪ್ರಾರಂಭಿಸಲು ಪ್ರಯತ್ನಿಸಿ - ನೆಟ್‌ವರ್ಕಿಂಗ್, VM ವಲಸೆ, ಇತ್ಯಾದಿ.
  • ಯುಪಿಡಿ: Qemu ಮತ್ತು ಇತರ ಯೋಜನೆಗಳ ಹಿಂದಿನ ಪೋರ್ಟರ್‌ಗಳು ಮಾಡಿದಂತೆ, ನಿಮ್ಮ ಕೆಲವು ಬೆಳವಣಿಗೆಗಳು ಮತ್ತು ದೋಷ ವರದಿಗಳನ್ನು ನೀವು Emscripten upstream ಗೆ ಸಲ್ಲಿಸಬೇಕಾಗುತ್ತದೆ. ನನ್ನ ಕಾರ್ಯದ ಭಾಗವಾಗಿ ಎಂಸ್ಕ್ರಿಪ್ಟನ್‌ಗೆ ಅವರ ಕೊಡುಗೆಯನ್ನು ಸೂಚ್ಯವಾಗಿ ಬಳಸಲು ಸಾಧ್ಯವಾಗಿದ್ದಕ್ಕಾಗಿ ಅವರಿಗೆ ಧನ್ಯವಾದಗಳು.

ಮೂಲ: www.habr.com

ಕಾಮೆಂಟ್ ಅನ್ನು ಸೇರಿಸಿ