- Bản port DOS dựa trên DJGPP đã được thêm vào SDL và được hợp nhất vào main với phạm vi hỗ trợ khá rộng, bao gồm video, âm thanh, nhập liệu, luồng, bộ hẹn giờ, hệ thống tệp và cả chuỗi công cụ build
- Đã có phần triển khai phù hợp với môi trường DOS cho video VGA và VESA 1.2+, phát âm thanh dòng Sound Blaster, bàn phím và chuột PS/2, joystick dựa trên BIOS, luồng hợp tác và bộ hẹn giờ PIT
- Vấn đề seek/read của DJGPP được обход bằng cách dump và khôi phục bộ đệm khi seek, qua đó loại bỏ lỗi đọc sai và độ trễ vài giây của
SDL_LoadWAV; đường đi âm thanh cũng được tinh chỉnh để giảm tái nhập IRQ và hiện tượng khựng tiếng
- Màn hình đen ở chế độ fullscreen có liên quan tới việc chọn mode INDEX8; thay vì thêm hint riêng cho DOS, phần này được điều chỉnh theo hướng sắp xếp thứ tự mode hợp lý hơn, còn lỗi độ trong suốt của con trỏ cũng đã được sửa bằng commit bổ sung
- Việc thử nghiệm trên phần cứng thật còn hạn chế; một số tính năng như ghi âm,
SDL_LoadObject, hay phần triển khai riêng cho DOS của SDL_TIME vẫn chưa có, nhưng thay đổi này đã vượt qua 46 kiểm tra để được hợp nhất và được xếp vào tính năng của 3.6.0
Phạm vi hỗ trợ của nền tảng DOS
- SDL đã được bổ sung bản port DOS và đạt tới mức độ hoàn thiện tương đối cao trên nền DJGPP
- Công việc được chia ra cho nhiều người thực hiện, và ở giai đoạn cuối có thêm các bản sửa ổn định cùng phần bù cho những tính năng còn thiếu
- DevilutionX đã được thử nghiệm rộng rãi trong DOSBox, nhưng không có thử nghiệm trên máy thật
- Một số tính năng cũng bị cố ý loại bỏ nếu không có cách kiểm thử phù hợp
- Các tính năng được hỗ trợ được liệt kê khá cụ thể
- Video bao gồm framebuffer VGA và VESA 1.2+, màu RGB và indexed 8-bit, lập trình bảng màu VGA DAC, vsync và page flipping bằng phần cứng, cùng lưu/khôi phục trạng thái VBE khi thoát
- Âm thanh hỗ trợ Sound Blaster 16, Sound Blaster Pro, Sound Blaster 2.0/1.x, dùng DMA dựa trên IRQ và đường đi auto-init với bộ đệm kép
- Nhập liệu gồm bàn phím PS/2 có hỗ trợ extended scancode, chuột INT 33h, và joystick gameport dựa trên BIOS INT 15h
- Luồng dùng bộ lập lịch hợp tác dựa trên
setjmp/longjmp và vá stack, đồng thời có fallback thông thường cho mutex, semaphore, TLS và condition variable
- Event pump và hàm delay có chèn điểm yield để duy trì độ phản hồi của âm thanh và các luồng khác
- Bộ hẹn giờ là phần triển khai dựa trên PIT dùng
uclock() của DJGPP với độ phân giải khoảng 1.19 MHz
- Hệ thống tệp xử lý
GetBasePath và GetPrefPath bằng searchpath() của DJGPP, đồng thời có fallback cho các thao tác hệ thống tệp POSIX
- Build bao gồm file toolchain cross-compile cho CMake, job CI cho DJGPP và preseed cache để cấu hình nhanh hơn
- Các tính năng chưa được đưa vào cũng được nêu rõ
- Ghi âm chưa có, chỉ hỗ trợ phát
- Phần triển khai native của
SDL_TIME không có riêng, mà tái sử dụng Unix gettimeofday thông qua lớp POSIX của DJGPP
- Nạp thư viện dùng chung không được hỗ trợ nên không có
SDL_LoadObject
Quá trình triển khai và các thay đổi chính
- Bản port DOS được bổ sung dần qua nhiều commit, từng bước thêm video, âm thanh, nhập liệu, bộ hẹn giờ, luồng và chuỗi build
- Sau phần công việc ban đầu, các mảnh còn lại như stdio buffering, triển khai âm thanh, subsystem video, hệ thống tệp, chuột, bàn phím, CI và nhận diện nền tảng được hoàn thiện theo thứ tự
- Ở stdio và truy cập tệp, nhóm phát triển đã обход vấn đề seek/read đặc thù của DJGPP
- Từng có thử nghiệm tắt bộ đệm của SDL_IOStreams dựa trên stdio, nhưng sau đó được thay bằng cách dump và khôi phục bộ đệm khi seek
- Cách này nhanh hơn nhiều so với việc tắt hoàn toàn bộ đệm, đồng thời tránh được lỗi đọc sai sau
fseek
- Hiện tượng
SDL_LoadWAV mất vài giây để đọc test/sample.wav đã biến mất, và dữ liệu đọc vào cũng trở nên chính xác
- Cách xử lý âm thanh cũng tiếp tục được điều chỉnh theo hướng ưu tiên độ ổn định
- Ban đầu bắt đầu từ phần triển khai Sound Blaster 16, sau đó được bổ sung hỗ trợ pre-SB16 8-bit mono và SB Pro stereo
- Việc trộn âm thanh từng được chạy trực tiếp trong IRQ handler, rồi chuyển qua main loop, sau đó lại dời sang luồng âm thanh của SDL
- Hướng đi này được chọn để tránh vấn đề tái nhập trong IRQ; đồng thời nửa bộ đệm DMA cũ trong lúc tải được ghi silence để giảm stutter
- Việc điều chỉnh sample rate, polling trạng thái DSP, cơ sở phân bổ bộ nhớ DMA, và cả việc tháo IRET wrapper sau khi khôi phục vector ngắt cũng đã được xử lý
- Video cũng được mở rộng chi tiết để phù hợp với các ràng buộc của môi trường DOS
- Một phần triển khai ban đầu hoạt động với software renderer qua giao diện VESA đã được thêm vào
- Sau đó tiếp tục có hỗ trợ bảng màu 8-bit, VBE page flipping, khôi phục trạng thái, vsync cho chế độ single-buffer, và chế độ framebuffer phân trang kiểu banked của VESA
- Khi VBE 1.2+ không có LFB, framebuffer được sao chép bằng bank switching; trong chế độ này page flipping sẽ bị vô hiệu hóa
- Toàn bộ trạng thái VBE được lưu và khôi phục khi khởi tạo và kết thúc video để việc chuyển mode diễn ra gọn gàng
- Xử lý nhập liệu và ngắt cũng đã được tinh chỉnh tới mức dùng thực tế
- Bàn phím xử lý cả extended scancode lẫn phím Pause, và dùng một ring buffer đơn giản để lưu sự kiện
- Chuột dùng function
0x1B của INT 33h để truy vấn độ nhạy
- Joystick giới hạn polling trục xuống khoảng 60 Hz để giảm chi phí timing loop của BIOS, trong khi nút bấm vẫn luôn được polling trực tiếp để giữ độ phản hồi
- Mã ISR và dữ liệu của nó được khóa để tránh page fault trong lúc xử lý ngắt
- Các vấn đề về build và nhận diện nền tảng cũng được sửa
- Đã có thêm job CI cho DJGPP và phần nhận diện nền tảng DOS trong CMake
SDL_PLATFORM_DOS được đưa vào danh sách loại trừ của SDL_RunApp() để tránh xung đột với launcher riêng cho DOS
- Dù DJGPP định nghĩa
__unix__, DOS không có GTK hay display server, nên SDL_Gtk_Quit() được loại khỏi DOS để tránh lỗi liên kết
- Cũng đã tính tới việc một số toolchain DJGPP dùng tiền tố
i386-pc-msdosdjgpp-gcc
Tình trạng kiểm thử và các hạn chế còn lại
- Các bài kiểm thử tự động không hoàn tất trơn tru hoàn toàn, nhưng đã đạt tới mức có thể chạy hết bằng patch
- Một số vấn đề ở các hàm formatting chuẩn khiến kiểm thử tự động không thể chạy tới cuối; nhóm đã dùng patch обход để hoàn tất việc kiểm thử
- Vẫn còn vài trường hợp thất bại, nhưng chưa chắc cách sửa đúng cho các hàm formatting đó nên chưa đưa vào
- Phần lớn demo nhìn chung hoạt động ở mức có thể kỳ vọng được
- Kết quả sử dụng thực tế cũng được bổ sung
- Trên DOSBox và DOS 6.22 chạy trên bo mạch Vortex86, chế độ không fullscreen hoạt động tốt với cả chương trình thử nghiệm lẫn mã người dùng
- Tuy vậy, fullscreen ở thời điểm đó cho ra màn hình đen trống trong các ví dụ như
draw.exe --fullscreen
- Tốc độ có chậm nhưng vẫn được đánh giá là dùng được
- Một số vấn đề của các chương trình thử nghiệm cũng được xác nhận
sprite.exe thoát ngay trong DOSBox
wm.exe và draw.exe không render được, nhưng vẫn thoát nếu nhấn ESC
testpalette gây segfault
Vấn đề chọn độ sâu màu ở fullscreen và điều chỉnh
- Nguyên nhân trực tiếp của màn hình đen ở fullscreen là
SDL_GetClosestFullscreenDisplayMode() rơi xuống mode INDEX8
- Nếu ứng dụng không xử lý render INDEX8 thì màn hình sẽ thành màu đen
- Trong phần triển khai nội bộ, INDEX8 chỉ được xét tới khi người dùng đã thiết lập mode fullscreen INDEX8 từ trước
- Ban đầu đã có một cách xử lý là ẩn mode INDEX8 phía sau
SDL_HINT_DOS_ALLOW_INDEX8_MODES chỉ trên DOS
- Mục tiêu là chỉ cho phép opt-in một cách rõ ràng khi ứng dụng thực sự xử lý đúng được
- Tuy nhiên, trên nhánh main đã có thay đổi chọn bit depth cao nhất thay vì thấp nhất, và sau đó có quá trình kiểm tra xem như vậy có giải quyết được hay không
- Thay đổi này sửa được vấn đề bpp, nhưng lại tạo ra lỗi mới là yêu cầu best fit 640x480 lại chọn 1024x768
- Cuối cùng thay đổi đó bị hoàn tác, và hướng sửa tốt hơn được tách sang một PR khác
- Về sau, hint riêng cho DOS bị loại bỏ và thay bằng việc sắp xếp thứ tự mode theo logic hơn
- Commit
Remove SDL_HINT_DOS_ALLOW_INDEX8_MODES and order modes logically đã được thêm vào
- Khi #15442 được hợp nhất, kết luận là ngay cả các ứng dụng không tự đặt palette hoặc không tự chọn mode fullscreen cũng có thể hoạt động đúng với cơ chế tự chọn mode
- Đồng thời cũng vạch rõ rằng PR này sẽ không tiếp tục đào sâu vô hạn các vấn đề khác vốn đã có sẵn trong SDL
Sửa lỗi render demo và con trỏ
- Việc demo hiển thị màu đen không phụ thuộc riêng PR này mà còn tùy vào việc #15442 đã được hợp nhất hay chưa
- Khi
SDL_GetClosestFullscreenDisplayMode() còn ưu tiên độ sâu màu thấp nhất, bản port này sẽ chọn INDEX8, và nếu ứng dụng không đặt palette thì màn hình sẽ bị đen
- Có xác nhận rằng sau khi hợp nhất PR đó cục bộ, toàn bộ đối tượng thử nghiệm đều hoạt động
- Vấn đề hình ảnh còn lại là độ trong suốt của con trỏ
- Sau khi kiểm tra cục bộ, người ta phát hiện chỉ riêng con trỏ là không trong suốt
- Để sửa điều này, commit
Don't convert cursor if dest is not INDEX8 đã được thêm vào
- Sau khi sửa, ở mode RGB hệ thống dùng phiên bản chưa được tối ưu, nhưng đã hoạt động đúng cho cả RGB lẫn INDEX8
- Vẫn còn dư địa cải thiện hiệu năng đôi chút ở XRGB1555 và RGB565, nhưng được xem là ưu tiên thấp
Review và quyết định hợp nhất
- PR này được đánh giá là phù hợp để squash merge
- Vì GitHub vẫn giữ tham chiếu tới PR trong commit kết quả, quá trình làm việc vẫn có thể được lần theo
- Cũng có đề xuất thêm ghi nhận công lao bổ sung vào commit kết quả
- Thậm chí còn kèm theo câu chữ cụ thể để thêm
Co-authored-by cho hai người và Tested-by cho một người
- Reviewer cho biết sau khi hợp nhất sẽ viết lại gọn hơn một số biểu đạt trong script build
- Ngay trước khi hợp nhất cuối cùng, hướng xử lý được chốt là hợp nhất cả các PR liên quan khác rồi tiếp tục PR DOS
- Sau “Last call on DOS pull request!”, trạng thái hợp nhất của các PR liên quan đã được xác nhận
- Tiếp đó, thay đổi này được hợp nhất vào main với trạng thái 46 checks passed
- Sau khi hợp nhất, phạm vi phát hành cũng được chốt rõ
- Thay đổi này được xem là tính năng của 3.6.0
-
Không cherry-pick sang 3.4.x
- Một ngày sau khi hợp nhất, nhánh làm việc DOS đã bị xóa
Công việc tiếp theo và các vấn đề phần cứng còn lại
- Cũng có ý kiến nêu ra rằng phần triển khai
4f07(SetDisplayStart) của một số GPU Nvidia không hoạt động đúng
- Kèm theo liên kết chuỗi thảo luận VOGONS, nội dung cho biết có những GPU được báo là hỗ trợ nhưng thực tế lại không hoạt động
- Phạm vi có thể từ GeForce 9300 tới 3060 theo thiết bị đang có, nhưng đây không phải phạm vi đầy đủ
- Trong quá trình kiểm thử phía dự án cũng đã quan sát thấy cùng hiện tượng hiển thị đó
- Nhóm phát triển cho rằng cách SDL tắt tính năng theo từng hãng GPU là không lý tưởng, và cũng nhắc tới khả năng dùng hint cho người dùng tự điều khiển
- Một hint mới để người dùng tự điều khiển
page_flip_available có thể là hướng tốt hơn
- Vấn đề này chưa được xử lý ngay mà để dành cho sau
- Sau khi hợp nhất, một hint cho phép dùng framebuffer trực tiếp cũng được nhắc tới
- Có ghi rõ rằng nếu bật
SDL_HINT_DOS_ALLOW_DIRECT_FRAMEBUFFER, vấn đề SetDisplayStart ở trên có thể sẽ bớt quan trọng đi
1 bình luận
Ý kiến Hacker News
Giờ chỉ cần có SDL cho UEFI là có thể chạy game ngay trong môi trường trước khi khởi động OS
Cũng muốn biết bảo mật đã được siết chặt hơn chưa, hay vẫn còn có thể truy cập được https://www.zdnet.com/article/minix-intels-hidden-in-chip-operating-system/
Chỉ là theo tôi biết thì UEFI không có trình điều khiển âm thanh, mà dạo này ngay cả chip codec âm thanh cũng chỉ có datasheet dành riêng theo NDA, nên tự viết cũng khá khó
Còn tréo ngoe hơn là graphics output protocol không có thông tin vsync, nên không thể blitting không xé hình, đúng nghĩa là còn tệ hơn cả VGA
Cứ tưởng tượng boot bằng menu kiểu grub rồi hiện ra cả danh sách game cổ điển thì khá phấn khích
Điều làm ảnh chụp màn hình này đặc biệt buồn cười là vì chính DosBOX cũng được xây dựng trên SDL
Cái này dùng DJGPP, nên chuyển CPU sang chế độ 32-bit bằng DPMI
Vì thế sẽ không còn cảm giác old-school thật sự với segmented memory, near pointer và đủ loại giới hạn 64KB xuất hiện khắp nơi
Ngầu đấy
Tự nhiên thấy tò mò nếu dùng cùng các file thực thi MS-DOS đích 386+ của FreeBASIC, vốn hỗ trợ SDL binding, thì sẽ ra sao
[1] - https://github.com/freebasic/fbc
Tôi đã ấp ủ nhiều năm chuyện port lại OHRRPGCE, vốn ban đầu sinh ra từ DOS, trở lại DOS
Và nghĩ đến việc SDL từng mạnh tay loại bỏ gần như mọi bản port và hỗ trợ OS có từ thời SDL 1.2, thì việc SDL3 giành lại hỗ trợ DOS thật sự khá bất ngờ
Quá hoàn hảo
Sáng nay tôi đang phát triển bằng Turbo C bên trong DOSBox-X bên trong Debian GNU/Linux bên trong VMware Fusion bên trong macOS, nên đúng là tin quá hợp lúc
Tôi còn nhớ mang máng đã từng làm việc với turboc từ vài chục năm trước
Nói chính xác thì chuyện này trước đây đã làm được bằng HXDOS
Vì nó giả lập DirectDraw đủ tốt để SDL có thể dùng được
Vậy không biết nó được biên dịch cho đích SDL nào
Là toàn màn hình độc quyền Win32, hay là độ phân giải VESA kiểu 640x480?
Với một dự án mã nguồn mở như SDL, việc có thêm hỗ trợ kiểu này thường phụ thuộc vào mức độ xâm lấn của thay đổi, và liệu người đóng góp có thực sự tiếp tục bảo trì hay không
Mỗi dự án có chính sách khác nhau, và tôi không biết chính sách của SDL, nhưng vì họ đã có nhiều bản port rồi nên chắc họ hiểu rõ mình đang gánh gì
Ví dụ tôi thích nhất là openbsd luna88k https://www.openbsd.org/luna88k.html
Tôi hoàn toàn không biết có bao nhiêu người thực sự dùng nó. Có lẽ đó là một cỗ máy khá hiếm chỉ được phát hành ở Nhật, và nếu có người dùng thì phần lớn chắc cũng ở Nhật nên ngoài tầm nhìn của tôi; vì thế theo cảm nhận của tôi thì người dùng duy nhất chính là người port
Thế mà ở mỗi bản phát hành, vài tuần sau ngày công bố chính thức, họ lại như từ trong rừng bước ra và đăng lên các file và gói luna88k
Có khi chỉ vì biên dịch ngay trên máy luna88k thật nên mất nhiều thời gian; dù sao như vậy cũng đủ để nó tiếp tục được giữ như nền tảng phần cứng chính thức của OpenBSD
Bản thân tôi không hề muốn sở hữu luna88k, nhưng tôi thật sự kính phục người đã khiến nó tiếp tục chạy được như thế
Cảm giác như SDL đang quay trở lại cội nguồn thời Loki
Ngầu thật
Tại sao à? Chẳng vì lý do gì cụ thể, chỉ cần ngầu là đủ
Chỉ cần nhìn vào Internet Archive là thấy, miễn có bàn phím và chuột thì mức độ phức tạp cỡ AAA giữa thập niên 90 về cơ bản có thể chạy ở gần như mọi nơi
Những game như Tomb Raider, Command & Conquer, Quake là ví dụ, và nếu bạn muốn một nền tảng cứ thế mà chạy, thì đây là một lựa chọn khá hấp dẫn
Có thêm SDL thì mọi thứ còn dễ hơn nhiều
Thật sự rất vui
Điều này làm tôi cực kỳ hạnh phúc