2 điểm bởi GN⁺ 2024-11-12 | 1 bình luận | Chia sẻ qua WhatsApp
  • Do Typepad ngừng hoạt động, các chủ blog hiện tại phải tự xử lý việc có chuyển tên miền và nội dung hay không trong tình trạng không thể đăng nhập và truy cập tệp
  • Ngày ngừng dịch vụ là 30/09/2025; sau đó, việc đăng nhập tài khoản sẽ không còn được cung cấp
  • Với khách hàng đã trả phí hằng năm cho khoảng thời gian sau ngày ngừng dịch vụ, khoản hoàn tiền theo tỷ lệ đã được phát hành; nếu không thấy thông tin hoàn tiền, cần kiểm tra với ngân hàng
  • Tất cả dữ liệu blog sẽ bị xóa; ngoài các yêu cầu liên quan đến thông tin cá nhân, sẽ không có gia hạn truy cập hay kênh khôi phục nào được cung cấp
  • Các tên miền đăng ký qua Typepad Domains sẽ được chuyển sang Reseller Club vào ngày 27/10/2025; để kết nối với nền tảng mới, cần xóa CNAME Typepad hiện có

Xử lý tài khoản và dữ liệu sau khi ngừng dịch vụ

  • Ngày ngừng dịch vụ của Typepad là 30/09/2025
  • Sau ngày ngừng dịch vụ, người dùng sẽ không còn có thể đăng nhập vào tài khoản
  • Với khách hàng đã trả phí dịch vụ hằng năm cho khoảng thời gian sau ngày ngừng dịch vụ, khoản hoàn tiền theo tỷ lệ đã được phát hành
    • Nếu không thấy khoản hoàn tiền trên sao kê, cần liên hệ ngân hàng
    • Nếu không có thẻ tín dụng hợp lệ được đăng ký, việc hoàn tiền có thể chưa được xử lý
  • Sau khi ngừng dịch vụ, quyền truy cập tệp sẽ bị chấm dứt và cũng không có gia hạn riêng
  • Tất cả dữ liệu blog sẽ bị xóa; các yêu cầu liên quan đến thông tin cá nhân cần gửi tới privacy@newfold.com

Chuyển Typepad Domains và kết nối blog mới

  • Typepad Domains là đại lý bán lại của LogicBoxes; tất cả tên miền đăng ký tại Typepad Domains sẽ được chuyển sang một đối tác LogicBoxes khác là Reseller Club vào ngày 27/10/2025
  • Những người dùng liên quan sẽ nhận thêm email hướng dẫn từ Reseller Club
  • Không cần chuyển tên miền khỏi LogicBoxes sang nơi khác; sau đó vẫn có thể tiếp tục quản lý thông qua Reseller Club
  • Để kết nối tên miền với dịch vụ hoặc nền tảng blog mới, cần xóa bản ghi CNAME đang trỏ tới Typepad và thiết lập theo yêu cầu của dịch vụ mới
    • Trước ngày 27/10/2025, đăng nhập vào Typepad Domains để cấu hình
    • Sau ngày 27/10/2025, đăng nhập vào Reseller Club để cấu hình
  • Ngay cả khi dùng nhà đăng ký khác không phải Typepad Domains, bạn cũng cần xóa bản ghi CNAME trỏ tới Typepad tại nhà đăng ký đó và thiết lập để trỏ tới dịch vụ hoặc nền tảng blog mới
  • Độc giả muốn tìm một blog cụ thể cần liên hệ trực tiếp với blogger đó để hỏi blog đã được đăng lại ở đâu
  • Các câu hỏi bổ sung có thể được gửi qua điện thoại hoặc chat của Network Solutions

1 bình luận

 
GN⁺ 2024-11-12
Các ý kiến trên Hacker News
  • Có một bản vá đang được xem xét: https://inbox.sourceware.org/libc-alpha/cover.1722193092.git...
    Nó bắt đầu vì https://issues.redhat.com/browse/RHEL-42410, và là vấn đề độ ổn định của graphics stack mà vì lý do nào đó ít nổi bật hơn trên RHEL 9
    Ít nhất tôi kỳ vọng bản vá đầu tiên, tức sửa tính an toàn luồng của getenv, sẽ được đưa vào glibc 2.41, và việc backport có vẻ cũng khá an toàn
    setenv tương đối dễ xử lý vì glibc vốn đã không bao giờ giải phóng chuỗi biến môi trường; phần khó là unsetenv đồng thời
    Nếu không có cách làm kiểu snapshot, getenv có thể trả về con trỏ null thay vì giá trị biến môi trường thực sự đã được đặt
    Tôi không muốn đặt khóa vào getenv, vì getenv dùng không kèm setenv đã từ rất lâu được xem là async-signal-safe, và thêm khóa rất dễ làm hỏng ứng dụng
    Việc sửa xử lý environ gây tranh luận hơn một chút vì phức tạp trong việc tránh rò rỉ bộ nhớ do vfork+execve, nhưng các bản sửa bổ sung này ít quan trọng hơn đối với độ ổn định của graphics stack

    • Tôi nghĩ có thể đưa các biến được thêm sau khi tiến trình khởi động vào một linked list và triển khai theo cách nguyên tử
      Nếu độ dài trở nên quá lớn, luồng chạy setenv có thể tạo một hashmap mới và thay thế con trỏ cũ bằng con trỏ mới một cách nguyên tử
      Chỉ cần dùng một cờ nguyên tử cho biết hiện có đang rehash hay không để tránh hai luồng rehash cùng lúc
      Trong lúc đó, nếu luồng khác gọi setenv thì các biến bổ sung sẽ được nối vào list, rồi được xử lý ở lần gọi setenv sau
      Nếu có đủ nhiều luồng gọi setenv rất nhanh, list có thể phình ra vô hạn, nhưng setenv không thường được gọi, nên sự đơn giản của thay thế con trỏ nguyên tử có vẻ đáng giá
    • Có thể liên quan: "Setenv Is Not Thread Safe and C Doesn't Want to Fix It" (2023) -- https://www.evanjones.ca/setenv-is-not-thread-safe.html và bình luận HN về cách Rust bị ảnh hưởng: https://news.ycombinator.com/item?id=38342642
      Một quả mìn dưới chân đã tồn tại hàng chục năm, thật bực bội
  • Thật sự biết ơn vì ngày nay Steam chạy tốt như vậy trên Linux
    Tôi không xem nhẹ công sức âm thầm phía sau để biến điều đó thành hiện thực cho chúng ta

    • Hy vọng họ sớm phát hành lại bản chính thức của SteamOS
      Tôi muốn dựng một tháp PC chơi game dựa trên nó
      Có thể thỏa hiệp với Bazzite, nhưng nói thật là tôi muốn dùng SteamOS
  • Tôi nghĩ best practice chẳng phải là đọc mọi biến môi trường khi khởi động và tuyệt đối không dùng setenv sao
    Nơi duy nhất setenv có ý nghĩa là khi khởi chạy tiến trình mới, mà ngay cả trong trường hợp đó, có vẻ đúng hơn là tạo một environ mới bằng cách sao chép environ hiện tại rồi cập nhật giá trị mới
    Dùng getenv/setenv như một cơ chế messaging liên lạc giữa các tiến trình là cách kéo theo nhiều vấn đề, ngoài chuyện trên Linux lịch sử từng không an toàn luồng, còn có khả năng rò rỉ bộ nhớ tiềm ẩn, v.v.
    Bài viết dường như bỏ qua phần này khi nói rằng trên macOS thì nó an toàn luồng

    • Không. Bạn có thể dùng phải thư viện gọi getenv()
      Java làm theo cách đã nói, nhưng trong mã JNI dùng một thư viện muốn gọi getenv(), vấn đề vẫn phát sinh
  • Câu hỏi thật sự là: có trường hợp nào ta gọi setenv trong một luồng và thực sự muốn thay đổi đó áp dụng cho các luồng khác đã tồn tại không?
    Dù vậy, GLIBC có tài liệu khá đầy đủ về các hàm nguy hiểm, nên có thể tự thêm khóa hoặc sao chép

    • Một ý tưởng thú vị
      Chắc chắn có những chương trình kỳ vọng setenv thay đổi mảng environ, và có khả năng không chỉ coi nó là con trỏ mờ để truyền cho posix_spawn/execve
      Nếu muốn setenv theo từng luồng thì cũng cần biến environ theo từng luồng
      Nhưng điều này không hợp với POSIX lắm, vì environ không được khai báo trong header và lập trình viên phải tự viết khai báo extern char **environ; trong mã nguồn
      Khai báo này không tương thích với trường hợp environ là biến thread-local
    • Nếu thư viện phụ thuộc bên thứ ba dùng getenv/setenv thì bạn không thể tự thêm khóa hoặc sao chép
      Bài viết cũng đề cập phần này như một vấn đề dai dẳng của Steam client
    • Thực tế là plugin có đặt biến môi trường, rồi các worker thread đã khởi động trước đó sẽ đọc giá trị đó về sau
      Trường hợp của tôi thì các worker thread đều đang ngủ trong hàng đợi thực thi nên không thành vấn đề, nhưng về mặt kỹ thuật đó là tình huống muốn đặt biến môi trường trong một luồng và đọc nó từ luồng khác đang chạy
    • Glibc có thể tham khảo Illumos, vốn có putenv()/setenv()/unsetenv()/getenv() an toàn luồng
    • Có rất nhiều cách tốt hơn nhiều để liên lạc giữa các tiến trình, nên không cần dùng cấu hình getenv/setenv hacky và nguy hiểm như vậy
      Tôi không biết thư viện threading nào lại không có shared memory hoặc truyền thông điệp
      Có lẽ tình huống này chủ yếu xảy ra kiểu tiến trình chính thay đổi biến như HTTPS_PROXY, còn các luồng khác chạy thư viện kiểm tra biến đó trước khi mở TCP socket
  • Nhân tiện, quyết định để rò rỉ bộ nhớ trên Mac thực ra bắt nguồn từ FreeBSD khoảng 26 năm trước: https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=5604
    OSX đã kế thừa điều này, và cũng không ngạc nhiên nếu setenv của Windows có khả năng thuộc dòng BSD vì vấn đề giấy phép
    Ngay cả 26 năm trước người ta đã biết API này bị hỏng, nhưng không sửa vì quán tính: sửa sẽ làm các chương trình vốn có lỗi còn hỏng thêm
    Hầu như không nên có nhu cầu thay đổi biến môi trường của chính tiến trình của mình
    Với tiến trình con thì chỉ cần dùng hàm exec phù hợp; ngoài ra, thay vì thay đổi biến toàn cục rồi hy vọng đoạn mã ở xa sẽ đọc lại và xử lý đúng, nên gọi một API rõ ràng

    • Tôi chỉ đồng ý một phần với cảm giác “không thể sửa được”
      Với API hiện tại thì đúng, nhưng chỉ cần thay đổi API một chút là có thể làm được
      Chỉ cần strdup() giá trị trước khi getenv() trả về, rồi để lập trình viên giải phóng bộ nhớ sau khi dùng
      Nếu cho rằng giá trị có thể thay đổi, lập trình viên phải gọi lại getenv(), nhưng đây có vẻ là một thỏa hiệp hợp lý
      Thay đổi này sẽ làm các chương trình cũ bị rò rỉ bộ nhớ mỗi khi gọi getenv() mà không free(), nhưng phiên bản hiện tại cũng đã rò rỉ bộ nhớ, nên có vẻ không phải vấn đề chí tử
      Thêm nữa, phiên bản mới có thể bọc strdup() bằng mutex và xử lý setenv() tương tự để làm cho nó an toàn luồng
  • Có người đồng nghiệp gọi setenv là “API Linux tệ nhất”, nhưng setenv có thật sự là API Linux không?
    Nó không do Linux định nghĩa mà nằm trong POSIX, cũng không do kernel Linux triển khai; tất cả đều ở không gian người dùng

    • Nếu đang làm phần mềm ứng dụng cho Linux, còn các nền tảng hỗ trợ khác là Windows và macOS, thì đúng
      Tác giả bài gốc và đồng nghiệp có vẻ đang hỗ trợ Steam tại Valve, nên bối cảnh là như vậy
      Lý do người đồng nghiệp đó gọi nó là tệ nhất không phải vì đặc tả POSIX
      POSIX chỉ nói hàm này không bắt buộc phải an toàn luồng, chứ không ngăn việc làm cho nó an toàn luồng
      Vấn đề là triển khai cụ thể của glibc, thư viện C được dùng trên mọi bản phân phối Linux mà Valve hỗ trợ Steam, và tất cả các bản phân phối đó đều được gom dưới tên “Linux”
    • Nói chính xác thì đây là ràng buộc của GNU libc
      Nếu libc muốn thì có thể làm cho nó an toàn luồng
      Những ngôn ngữ như Go tự triển khai chức năng này nội bộ nên không có ràng buộc như vậy
      Bản thân tài liệu POSIX cũng đã tính đến giới hạn này: “The setenv() function need not be thread-safe.”
  • Với tư cách là người lớn lên cùng nethack và cờ vua trên Linux, sự tồn tại của Steam tự thân đã là điều đáng kinh ngạc
    Nhưng client Steam thì thật sự kỳ lạ
    Nó chạy ổn trong vài tháng rồi đột nhiên game không khởi động được hoặc có thứ gì đó không hoạt động, và phải làm những việc kỳ quặc như xóa mọi tệp hoặc cài lại thì mới chạy lại
    Thật vô lý, có cảm giác client Steam đang mục ruỗng dần

    • Steam là một trong những phần mềm tệ nhất, và thành thật mà nói, với một công ty lớn như vậy thì mức đó khá đáng xấu hổ
      Nó là một mớ hỗn độn pha trộn các nguyên tắc thiết kế khác nhau, còn tính năng mới thì chỉ được gắn thêm với UI và UX hoàn toàn khác
      Phần lớn client là webview, vừa chậm vừa nhiều lỗi, và bên trong dùng một phiên bản Chromium rất cũ và không an toàn
      Trình khởi chạy đến giờ vẫn là chương trình 32-bit
      Chỉ buồn là các launcher khác còn tệ hơn
    • Theo kinh nghiệm của tôi, những vấn đề đó cũng đều xảy ra với Steam trên Windows
      Ngược lại, từ khi chỉ dùng Linux thì tôi ít gặp những chuyện đó hơn
  • Đây là nội dung thật sự thú vị, cho thấy cả client Steam lẫn lập trình Linux
    Tôi hiểu rằng khó có thể viết ghi chú phát hành chi tiết cho từng bản phát hành, nhưng khi biết những công việc như thế này thì cụm “sửa một số lỗi crash phổ biến” đúng là một cách nói giảm nhẹ quá mức

  • Phần “nếu có thể giải quyết vấn đề này trong glibc thì có thể cần một số thỏa hiệp về chức năng, hoặc có thể là một cơ chế opt-in hơi lệch khỏi đặc tả POSIX ‘bất khả thi’. Nếu có thể đề xuất một phương án hợp lý thì về dài hạn có thể thúc đẩy” — tôi thật sự mong họ làm như vậy

  • Tôi thật sự tò mò vì sao lại dùng setenv(3) nhiều đến thế
    Công dụng chính tôi nghĩ đến là đặt biến môi trường trước khi gọi thứ gì đó như exec(3), nhưng ở đây có vẻ không phải trường hợp đó
    Bài viết nói rằng khi khởi chạy tiến trình con họ dùng exevpe, nên tôi thắc mắc còn việc gì cần dùng setenv(3) nữa

    • Có thể dùng nm -D để kiểm tra việc dùng setenv/unsetenv/putenv, và chỉ nhìn qua ~/.cargo/bin/* của tôi cũng thấy có quá nhiều chương trình dùng những thứ đó
      Có thể chúng là đơn luồng, nhưng ai bảo đảm được sau này vẫn luôn như vậy
      Nghĩ lại thì cũng có thể phát hiện pthread_create bằng danh sách symbol
      Sẽ thú vị nếu có phương pháp phân tích binary tĩnh để lần từ các symbol này tới tận cây lời gọi
      Tuy nhiên tôi không thấy cách nào kiểm tra việc dùng **environ. Trình biên dịch có thể biến nó thành bất cứ thứ gì