3 पॉइंट द्वारा GN⁺ 2023-09-01 | 2 टिप्पणियां | WhatsApp पर शेयर करें
  • Marginalia Search ने हाल के बदलावों से RAM की आवश्यकता आधी कर दी और अपग्रेड के दौरान search engine को बंद करना पड़ता था, उस operational बोझ को काफी कम किया
  • समस्या latest release के बाद index switching प्रक्रिया में सामने आई, और upgrade के समय URL database को मिटाने वाली संरचना ने लंबे समय तक offline रहने की स्थिति पैदा की
  • URL storage, विशाल MariaDB table और index-केंद्रित ढांचे से बदलकर एक single SQLite database और process-जनित 64-bit URL ID संरचना में आ गया
  • inverted index बनाना अब dense term ID के लिए lexicon और बड़े पैमाने की random writes को छोड़कर, छोटे preindex बनाकर उन्हें merge करने वाले तरीके में बदल गया है
  • नई संरचना bad deploy की स्थिति में भी कुछ घंटों में restore हो सकने वाले file backup को संभव बनाती है, और Wikipedia जैसे कम बदलने वाले बड़े data processing परिणामों को दोबारा इस्तेमाल करना आसान करती है

एक हफ्ते में search engine संचालन की शर्तें बदल गईं

  • Marginalia Search ने एक हफ्ते की coding से कई लंबे समय से चले आ रहे मुद्दों को एक साथ कम किया
    • search engine की RAM आवश्यकता आधी हो गई
    • upgrade के दौरान system को offline करना अब जरूरी नहीं रहा
    • index किए जा सकने वाले documents की hard limit हट गई
    • corpus में शामिल किए जा सकने वाले keywords की soft limit 4 गुना बढ़ गई
  • कम क्षमता वाले hardware पर भी system को चलाने लायक बनाए रखना लंबे समय का लक्ष्य था, और यह बदलाव उस पिछले सुधार से भी बड़ा है जब 32GB RAM वाली development machine आरामदायक लगने लगी थी

पुरानी upgrade संरचना जिसने outage को बढ़ाया

  • Marginalia Search, latest release की समस्याओं के कारण लगभग एक हफ्ते तक offline रहा
  • सीधा कारण अपेक्षाकृत मामूली scalability समस्याओं की एक श्रृंखला थी, लेकिन उस process को कई बार restart करना पड़ा जो सामान्य स्थिति में 1 दिन और समस्या होने पर 2–3 दिन लेता था
    • अधिकतर restart RAM की कमी के कारण हुए
  • यह outage उपयोगकर्ताओं को इसलिए ज्यादा दिखाई दिया क्योंकि index switching के दौरान system को offline करना पड़ता था
  • पुरानी संरचना में upgrade के दौरान URL database मिटा दिया जाता था, और लगभग 1 अरब rows वाली table में rows को तेज़ी से insert और update करना bottleneck बन जाता था
    • नया data load करने वाली process बहुत RAM इस्तेमाल करती थी
    • RAM का उसी तरह उपयोग करने वाली index service के साथ इसे एक साथ चलाना मुश्किल था
    • primary key 32-bit integer थी, इसलिए 2 अरब से आगे जाना कठिन था

URL database का redesign

  • URL database search engine का एक पुराना component था, और शुरुआती design decisions अब मौजूदा system architecture से मेल नहीं खा रहे थे
  • इसके केंद्र में दो tables थीं, जिन्हें केवल नया index load करते समय लिखा जाता था और केवल primary key lookup से पढ़ा जाता था
    • URL table हर URL को एक unique numeric ID देती थी
    • PAGE_DATA table indexed links के title और description जैसी जानकारी रखती थी
    • domain के भीतर path uniqueness बनाए रखने के लिए एक अतिरिक्त index था, लेकिन अपनी भूमिका की तुलना में वह बहुत बड़ा था
  • नई संरचना में इन दोनों tables को एक single-table SQLite database में मिला दिया गया, loader process unique ID generation संभालती है, और index न किए जाने वाले URL की सूची अलग table में रखी जाती है
  • MariaDB और SQLite को साथ इस्तेमाल करना कोई पारंपरिक विकल्प नहीं है, लेकिन दोनों storage अलग-अलग जरूरतें पूरी करते हैं
    • system को अपेक्षाकृत छोटा persistent world model चाहिए
    • साथ ही terabyte-स्तर के state को plug-and-play की तरह बदला जा सकना चाहिए
  • DOCUMENT और DOMAIN tables database के आर-पार ढीले तौर पर संबंधित हैं, लेकिन वास्तविक join की जरूरत नहीं है
    • disaster की स्थिति में DOMAIN table के महत्वपूर्ण हिस्से DOCUMENT table से फिर बनाए जा सकते हैं

index के बिना 64-bit URL ID बनाना

  • पुरानी URL table 32-bit ID इस्तेमाल करती थी, और integer overflow के करीब पहुंचना एक ज्ञात scalability समस्या थी
  • URL database को मिटाने का एक कारण यह भी था कि ID column overflow न करे
  • केवल simple counter से बार-बार आने वाले URL को संभालना संभव नहीं था, और देखे गए सभी URL का collection memory में बनाए रखना भी टालना था
  • नया तरीका database से ID allocate नहीं कराता, बल्कि सीधे 64-bit ID बनाता है
    • नीचे के 26 bits sequence number के लिए हैं
    • 26 से 56 bits document ID के लिए हैं
    • सबसे ऊपरी bits index sorting tricks के लिए reserve हैं
  • यह layout प्रति domain लगभग 6.7 करोड़ documents की अनुमति देता है
    • यह English Wikipedia के लगभग 10 गुना आकार के बराबर है
    • domains की संख्या 2 अरब तक हो सकती है
    • यह Marginalia द्वारा web पर कहीं भी reference में देखे गए domains की संख्या से लगभग 100 गुना ज्यादा है
  • data integrity की जिम्मेदारी database से data generation process पर चली जाती है, लेकिन वहां इसे enforce करने की लागत काफी कम है

URL redesign से memory पर घटा दबाव

  • विशाल indexes और hot/cold URL data के मिले-जुले बड़े table हटने से MariaDB server को अब 36GB RAM की जरूरत नहीं रही
  • MariaDB में बचा हुआ hot data अधिकतम कुछ सौ MB स्तर का है, और server को 2GB से ज्यादा RAM देने की जरूरत शायद नहीं होगी
  • SQLite data को भी primary key के लिए index चाहिए, लेकिन वास्तविक hot index हिस्सा 1GB से कम रहने की उम्मीद है
    • index किया जाने वाला data एक अंक के factor से कम हो गया है
    • index target एक single 64-bit long है
    • कोई अतिरिक्त unique constraint नहीं है
  • loader output अब file bundles के रूप में होने से automatic backup बनाना आसान हो गया है
  • bad deploy होने पर भी अब पहले की तरह लगभग एक हफ्ते नहीं, बल्कि कुछ घंटों में recovery संभव है

inverted index generation का bottleneck

  • loader, URL database और document-केंद्रित (document, words[]) journal output करता है, जबकि search के लिए इसे (word, documents[]) रूप में transpose किए गए index की जरूरत होती है
  • पुराना तरीका keyword strings को dense term ID से map करने के लिए lexicon इस्तेमाल करता था
    • पहला शब्द ID 0 पाता था, अगला शब्द ID 1
    • strings को 64-bit hash के जरिए long में map किया जाता था
    • यह संरचना मूल रूप से long-to-int open hashmap थी
  • scale बढ़ने पर यह संरचना आसानी से भर जाती थी
    • Java 2 अरब से बड़ी arrays की अनुमति नहीं देता
    • इस्तेमाल की जा रही implementation लगभग 1 अरब entries पर ही रुक जाती थी
    • 1 अरब entries पर 12GB RAM लगती थी
  • production में चल रही index service 60GB RAM इस्तेमाल करती है, और इसका अधिकांश हिस्सा off-heap memory है
  • on-heap size का 32GB से ऊपर जाना और CompressedOOPs का उपयोग मुश्किल हो जाना भी एक समस्या थी

पुराने inverted index algorithm की write amplification

  • पुराना algorithm सबसे बड़ा word ID ढूंढता था, उसके आकार का counts array बनाता था, फिर हर शब्द के document positions की गणना करके memory-mapped file में document data लिखता था
  • इस तरीके को lexicon की जरूरत इसलिए थी क्योंकि यह मानता था कि word ID का domain densely भरा हुआ है
  • बड़ा bottleneck यह था कि लगभग 1TB data को memory-mapped file में लगभग पूरी तरह random order में लिखा जाता था
  • SSD पढ़ने में random access अच्छा संभालते हैं, लेकिन छोटे writes में write amplification की समस्या आती है
    • SSD में disk के एक byte को update करने के लिए भी पूरी page को erase करके फिर लिखना पड़ता है
    • पास-पास के writes को जोड़ने वाले cache होते हैं, लेकिन terabyte-स्तर की random writes पर उनका असर नहीं पड़ता
    • 1TB लिखते समय drive वास्तव में लगभग 0.5PB लिख रही होती है
  • अस्थायी राहत के लिए RandomWriteFunnel था
    • writes को पहले छोटे file buckets में बांटा जाता था
    • बाद में बड़ी file क्रम से लिखी जाती थी
    • यह मूल तरीके से बेहतर था, लेकिन फिर भी बहुत धीमा था

छोटे preindex बनाना और उन्हें merge करना

  • नया inverted index generation तरीका कई छोटे indexes बनाता है, जिनका पूरा data memory में आ सके, और फिर उन्हें merge करता है
  • sorted list merge तेज़ होता है और mechanical hard disk पर भी अच्छी तरह काम करता है
  • इस तरीके में lexicon की जरूरत नहीं रहती
    • term ID के रूप में 64-bit string hash सीधे इस्तेमाल किया जा सकता है
  • शुरुआत में समस्या compressed input और index merge के तरीके की थी
    • compressed input के हिस्सों को तेजी से पढ़ने के बजाय, कई छोटी files बनाई गईं और उन्हें एक-एक करके पढ़ा गया
    • index बनाने के बाद merge करने के बजाय, index बनाने से पहले data merge किया गया
  • नई abstraction preindex में word ID array, count array और document data array शामिल हैं
  • input छोटा होने के कारण अधिकांश preindex RAM में बनाए जा सकते हैं, generation के दौरान disk पर commit किए जा सकते हैं, और बाद के merge चरण में final preindex बनाया जा सकता है
  • final preindex को बाद में पुराने तरीके की तरह words table और हर document block पर static btree index जोड़कर inverted index में बदला जाता है, और यह प्रक्रिया अपेक्षाकृत तेज़ है

operations और data reuse में आया बदलाव

  • lexicon हटने से RAM की आवश्यकता घटी, और नया inverted index generation पुरानी algorithm से तेज़ है
  • पुराना lexicon हर processed data batch के लिए एक अलग dialect बना देता था
    • एक run में एक शब्द को जो ID मिलती थी, दूसरे run में वही शब्द दूसरी ID पा सकता था
    • इसी कारण सारा data एक साथ process करना पड़ता था
  • lexicon छोड़ने से अलग-अलग data batches को merge करना संभव हो गया
  • Wikipedia जैसे बड़े और कम बदलने वाले data के processing results को reuse करके उन्हें ज्यादा बार बदलने वाले indexed data के साथ जोड़ा जा सकता है
  • इस बदलाव ने लगभग सभी ज्ञात scalability समस्याओं और operational असुविधाओं को कम किया, और अब अधिक side effects की समीक्षा करना संभव हो गया है

2 टिप्पणियां

 
GN⁺ 2023-09-01
Hacker News की राय
  • बाकी दुनिया से बिल्कुल उलटी दिशा में जाने वाले प्रोजेक्ट में ऐसी सफलता की कहानी देखकर सच में अच्छा लगता है
    मैं इसे Engildification कहना चाहूंगा, और ऐसी चीजें और ज्यादा होनी चाहिए
    Sleeping At Night वाला लेख भी पसंद आया, और हाल के “Lie Still in Bed” लेख के साथ यह sleep training की समस्या को ठीक करने का एक बेहद सरल विकल्प लगता है

    • यह scale का function लगता है। product के पीछे की team या company जितनी बड़ी होती है, enshittification का coefficient और संभावना भी उतनी ही बढ़ती है
      Marginalia search engine के लेखक ने हाल ही में full-time काम शुरू किया है, और जहां तक मुझे पता है team size 1 व्यक्ति है, इसलिए यह enshittification के जोखिम से सबसे दूर है। बल्कि इसी scale पर gems बनते हैं, और creativity, quirkiness और vision चमकते हैं
      यह comment “desk job छोड़कर independent होकर काम करें” समूह द्वारा प्रायोजित है
    • हाल के 3 लेखों को देखें तो सच में ताजगी महसूस होती है
      resource consumption आधा कर दिया, छोटे screen पर पहले से ज्यादा productive हो गए, और रात में लकड़ी के लट्ठे की तरह गहरी नींद सोते हैं
    • इस साल मैं sleep की समस्या से जूझ रहा हूं, इसलिए दूसरों के लिए काम आए तरीकों के बारे में जानना काफी useful है
      interested लोगों के लिए link: https://www.marginalia.nu/log/86-sleep/
    • engildification expression पसंद आया
    • ऐसे examples सच में हैं। बस Google से उन्हें कभी नहीं ढूंढ पाएंगे
  • संदर्भ के लिए, paid search engine Kagi, जिसे Hacker News पर भी देखा गया होगा, Marginalia को अपने data sources में से एक के रूप में इस्तेमाल करता है
    https://help.kagi.com/kagi/search-details/search-sources.htm...
    “non-commercial” lens इस्तेमाल करने पर Kagi के अपने index और कुछ independent sources के results के साथ ऐसे results को प्राथमिकता मिलती

  • यह लेख देखकर लगता है कि शायद इंसान कृत्रिम सीमाओं के बिना बेहतरीन चीज़ें बनाने में मुश्किल महसूस करने वाला प्राणी है
    Marginalia के बेतुके ढंग से efficient होने की वजह यह है कि Victor जानबूझकर execution hardware और memory capacity को सीमित रखते हैं
    बस 32GiB और जोड़ देने से कुछ समय तक काम तो चल जाएगा, लेकिन inefficient design बचा रहेगा, और बाद में जब सिस्टम और जटिल हो जाएगा तो वही समस्या फूटेगी और उसे ठीक करना कठिन हो सकता है
    अगर यह धारणा सही है, तो यह भी समझ आता है कि आज का software इतना फूला हुआ, धीमा और bug से भरा क्यों है। अलग-अलग software स्वतंत्र रूप से अपनी सीमा के करीब लगभग नहीं पहुंचते, इसलिए हर टुकड़ा inefficient होते हुए भी नए M2 Pro और GiB-स्तर की connectivity के सहारे समस्या वाली जगह से लगातार आगे निकलता रहता है
    निष्कर्ष यह हो सकता है कि खुद को सीमित रखना लंबी अवधि में अपने लिए और सबके लिए बेहतर है

    • अधिकतर यह priority का मामला है
      कई applications में छोटी-मोटी optimization पर इतना समय लगाना समझदारी नहीं है। जब server में 32GiB RAM 50 डॉलर से कम में जोड़ी जा सकती है, तो developer के 40+ घंटे कम-से-कम 20 डॉलर प्रति घंटे के हिसाब से लगाने के विकल्प की तुलना में business के नजरिए से जवाब साफ है। ऊपर से website पूरे हफ्ते down रही, और सिर्फ यही बात ज्यादातर businesses को खत्म कर सकती है
      तकनीकी लोग इस तरह गहराई में खोदना पसंद करते हैं, इसलिए मामूली code को भी सालों तक micro-optimize करना चाहते हैं, लेकिन अंतहीन yak shaving से पैसा नहीं बनता। अगर code बहुत कम machines पर ही चलता है, तो आमतौर पर यह करने लायक नहीं होता। ऐसी optimizations अक्सर ऐसे code पर खत्म होती हैं जिसे maintain करना और कठिन हो जाता है
      आजकल user devices पर चलने वाले apps की software bloat मुझे काफी हद तक developer devices और user devices के mismatch से आती लगती है। developer को काम करने के लिए high-performance workstation चाहिए और उसी पर basic testing भी होती है, लेकिन user इसे ऐसे device पर चलाता है जो 5 साल पहले भी mid-range से नीचे था
      manager को “150MB memory बचा सकते हैं” बेचना मुश्किल है, लेकिन “150MB memory बचाने से 10% users के लिए app performance भयानक से किसी तरह इस्तेमाल लायक हो जाएगी” बेचा जा सकता है
    • मैं इस नजरिए से सहमत हूं। सीमाएं ingenuity पैदा करती हैं, और यह सिर्फ demoscene outputs पर लागू नहीं होता। scalability की समस्याएं कभी-न-कभी मिलेंगी ही, और उन्हें देर से संभालने की बजाय जल्दी संभालना कहीं आसान है। अगर software Raspberry Pi पर ठीक चलता है, तो असली server पर वह अविश्वसनीय रूप से तेज होगा
      पहले सचमुच software इसी तरह बनाया जाता था। इसलिए Pentium 1 जैसी machines पर भी आज हम जिनमें से ज्यादातर चीज़ों की उम्मीद करते हैं, उनसे लैस operating system ठीक से चल सकता था। इसके उलट आज ऐसे smartphones पर भी web pages scroll करते समय अटकते हैं जिनके पास हर पैमाने पर सचमुच लगभग हजार गुना ज्यादा resources हैं। Word 95 team लगातार limits और performance trade-offs से टकराती थी, और नतीजा साफ तौर पर काम करता था या नहीं करता था
      अगर बस और RAM जोड़ दी जाती, तो वे फिर भी घटिया design में फंसे रहते, और जल्द ही फिर और RAM खरीदनी पड़ती। इस बदलाव की हैरान करने वाली बात यह है कि इसने सिर्फ resource usage घटाया नहीं, बल्कि spare RAM की वजह से disk cache बढ़ा और system ज्यादा सक्षम और तेज हो गया
      [1] उदाहरण के लिए, यह एक single Pi पर चलता है, और updates allow नहीं करता, इसलिए production में चल रही Wikipedia से कहीं तेज है: https://encyclopedia.marginalia.nu/article/Hacker_News
    • यह hypothesis मुझे भी पसंद है
      शायद इसलिए पुराने computers अच्छे लगते थे, और पुराने games भी इतने शानदार थे
      यह उन systems की complexity से जुड़ा हो सकता है जिनसे हम निपटते हैं। RAM, physical space, खाना, materials, समय, पैसे जैसे resources सीमित हों तो उनका इस्तेमाल कैसे करना है इसकी planning करनी पड़ती है, और चतुर होना ही पड़ता है
      जब resources व्यवहार में unlimited हों, तो आप जैसा चाहें वैसा बना सकते हैं, लेकिन final state की चिंता करने की जरूरत कम हो जाती है। बस शुरू कर दीजिए, चलने लगे तो देख लेंगे
      मैं सच में gamer नहीं हूं, लेकिन कुछ KB/MB ROM cartridges में इतनी भावनाएं, adventure और खेलने के इतने घंटे भर देने की इंसानी क्षमता देखकर हमेशा हैरान होता हूं। Ocarina Of Time ROM का size मेरे iPhone से ली गई हाल की करीब 8 photos जितना ही है
    • American Airlines ने 1970s के मध्य में ticketing और reservation system SABRE को दो System/360 mainframes पर चलाया था, और throughput सिर्फ प्रति सेकंड करोड़ों instructions के स्तर का था
      Raspberry Pi 2 प्रति सेकंड 4 अरब से ज्यादा Dhrystone instructions process कर सकता है, और Pi 4 प्रति सेकंड 10 अरब से ज्यादा
      बेशक आधुनिक मानकों से 1970s के मध्य का SABRE किसी airline के core system के हिसाब से काफी basic था, लेकिन सिद्धांत रूप में एक single Pi 2 पर 100 से ज्यादा airlines के simplified systems साथ-साथ चलाना भी संभव है
      आधुनिक programs optimization से बहुत दूर हैं। बहुत ज्यादा math-heavy cases को छोड़ दें, तो 1000x या 10000x improvement भी संभव है
    • अलग-अलग रूप से limit तक न पहुंचने वाली बात अच्छा point है
      मुझे लगता है Microsoft को यह समस्या बड़े पैमाने पर होती है। 5 साल पहले का 3000 डॉलर वाला laptop भी Teams call, कुछ Office apps और 30 tabs वाला browser साथ-साथ चलाने पर अस्वीकार्य रूप से धीमा हो जाता है
      अलग-अलग test करें तो एक ही चीज़ चलने पर ठीक रहता है, लेकिन असली लोग इस तरह इस्तेमाल नहीं करते
      साफ तौर पर defined hardware पर execution time को सीमित करना, और सिर्फ explicit decision के बाद ही उस limit को बढ़ाना—ऐसी artificial limits शायद solution हो सकती हैं
      हालांकि मैं सिर्फ ऐसा business software लिखता हूं जहां performance वाली बात आखिर में “database के साथ बेवकूफी मत करो, बाकी की चिंता मत करो क्योंकि customer उस चिंता के लिए पैसे नहीं देगा” तक सिमट जाती है, इसलिए शायद मैं पूरी तरह गलत भी हो सकता हूं
  • marginalia.nu update जब भी आता है, हमेशा अच्छा लगता है। यह इस site पर कीमती user है, और उम्मीद है आगे भी post करता रहेगा

  • धन्यवाद। मैं search engine hobby project कर रहा हूं, और न जाने क्यों लगातार “Magnolia” के variants ही search करता रहा। Marginalia नाम मुझे याद नहीं रहता। अभी Searx को समझ रहा हूं
    सोच रहा हूं कि क्या Marginalia पिछले एक दिन, पिछले हफ्ते जैसे time filter search support करता है। special keywords देखने पर लगता है कि search parameters सिर्फ year-based हैं
    year>2005 (beta) document देखने में 2005 के बाद published है
    year=2005 (beta) document देखने में 2005 में published है
    year<2005 (beta) document देखने में 2005 से पहले published है

    • search index महीने में एक बार से ज्यादा update नहीं होता, इसलिए ऐसे filters नहीं हैं
      year filters भी काफी rough हैं, और ज्यादातर webpages की dates ठीक-ठीक पकड़ना बहुत कठिन है
    • यह niche content के लिए search engine है। कहें तो peripheral content के लिए, इसलिए Marginalia नाम समझ आता है
  • यह सोच रहा हूँ कि “जब भी SSD डिस्क में कहीं किसी एक byte को update करता है, तो उसे पूरी page erase करके फिर से लिखनी पड़ती है” वाली बात सच में SSD पर लागू होती है या नहीं
    raw flash में ऐसा नहीं होता। अगर “खाली” all-ones value को overwrite किया जा रहा हो, या सिर्फ 1 को 0 में बदला जा रहा हो, तो यह संभव है। write, read से कई orders of magnitude धीमा होता है, लेकिन erase से भी कई orders of magnitude तेज़ होता है, और wear budget में सिर्फ erase ही गिना जाता है
    अगर SSD controller इसका फायदा नहीं उठाता, तो यह self-goal जैसा लगता है। हालांकि अगर अंदरूनी तौर पर यह सचमुच log-structured है, तो शायद ऐसा न कर पाए

    • यह situation पर निर्भर हो सकता है
      पहले मैंने कई लोकप्रिय flash chips के drivers लिखे थे, और जिन chips पर तब काम किया था, वे सभी read और write के लिए केवल fixed-size page-level I/O ही इस्तेमाल करते थे
      SSD chips का bundle होता है, इसलिए उम्मीद है कि SSD के अंदर हर chip भी सिर्फ fixed-size page I/O ही support करती होगी
    • इस मामले में असल में पूरा hard drive पूरी तरह random order में फिर से लिखा जा रहा था, और यह SSD के लिए worst case है
      आम तौर पर controller ऐसे worst patterns से बचने के लिए overprovisioning, buffering, write reordering जैसी कई techniques इस्तेमाल करता है, लेकिन limits होती हैं
    • मेरी समझ में यह ऐसा है
      SSD में लिखी जा सकने वाली सबसे छोटी unit page है, और erase की जा सकने वाली सबसे छोटी unit कई pages से बना block है
      इसलिए write operation page के सिर्फ 1 byte को भी affect करे, तब भी SSD सिर्फ उस byte को erase नहीं कर सकता। इसका मतलब यह भी नहीं कि हमेशा पूरा block erase करना ही पड़े
      SSD “read-modify-write” type का operation कर सकता है। बदले जाने वाले byte वाली पूरी page को SSD cache buffer में read करता है, page cache में सिर्फ उस byte को modify करता है, फिर एक खाली नया block erase करता है, modified page को cache से नए block में लिखता है, और FTL mapping table को update करता है ताकि वह नए block की updated page की ओर point करे
      इसलिए सिर्फ 1 byte बदलने पर भी page को फिर से लिखना पड़ता है। लेकिन जब तक उसके अंदर की कई pages modify न हों, पूरे block erase से बचा जा सकता है
    • बिल्कुल सही नहीं है। किसी specific flash address पर page रहती है—यह logical view असलियत से अलग है
      writes होते हुए page physical device के अंदर move होती है। drive खुद एक map maintain करती है कि कौन-सा address किस काम के लिए इस्तेमाल हो रहा है, उसकी health कैसी है, वगैरह। यह एक तरह का sparse storage approach है
      TRIM जैसे commands, periodic maintenance और garbage collection भी होते हैं
      असल में जो drive भरी नहीं है उस पर write करने पर, data रखने के लिए page खोजी जाती है, देखा जाता है कि वहाँ data है या नहीं, जरूरत हो तो read/modify/write किया जाता है, data कहाँ लिखना है तय किया जाता है और फिर लिखा जाता है। wear leveling के कारण उसके original location पर वापस जाने की संभावना कम होती है
      यह सही है कि controller performance के लिए कहीं ज्यादा complex steps करता है। इसलिए खाली नई drive कुछ समय तक बेहतर चलती है, और spare pages न होने वाली पुरानी, भरी हुई drive सचमुच धीमी भी हो सकती है
      source जोड़ूँ तो, मैं cache coherence वाले memory-mapped flash accelerator का lead engineer था। इसने Linux user space में drive को बहुत efficiently map करने दिया, लेकिन आखिरकार कुछ समय बाद यह एक और hard drive जैसा दिखने वाले “easy” programming model के आगे झुक गया
    • यह पूरी तरह गलत है। सबसे primitive SSD controller भी ऐसी situation को mitigate करने की कोशिश करता है
  • Mojeek में मेरे boss ने भी शायद इससे बहुत मिलता-जुलता रास्ता अपनाया होगा, यह याद आया। यह लेख पुरानी बातचीतों से काफी मेल खाता है
    Mojeek 2004 में शुरू हुआ था, और इसका ज्यादातर skeleton एक developer ने बनाया था, जिसने information retrieval और infrastructure का लगभग सब कुछ बनाया
    funding और hardware constraints, 32-bit बनाम 64-bit ID decision, sharding, update speed जैसी चीजें बहुत जानी-पहचानी लगती हैं
    पुराने Google का “Google dance” भी याद आता है। तब search results महीने में एक बार refresh होते थे, और अब रोज़ fluctuate करते हैं। यह सब evolution का हिस्सा है, और Marginalia का big tech से परे web को देखने का एक और नजरिया देना अच्छा लगता है

  • पढ़ने में अच्छा था
    बहुत से लोग optimization को गहरी black magic मानते हैं, लेकिन ज्यादातर मामलों में यह आम bug fixing से उल्टा आसान होता है। excessive resource usage को bug की तरह ही treat करना होता है
    मुझे लगता है, आसानी से reproduce होने वाले ज्यादातर bugs ठीक करने के लिए magic की जरूरत नहीं होती। अगर bug को poke किया जा सके, तो आम तौर पर उसे classify किया जा सकता है, और rare design flaws भी reproduce हो जाने पर अक्सर जल्दी सामने आ जाते हैं
    जिस software की performance को किसी ने critically नहीं देखा, वह ऐसे software जैसा है जिसमें आसानी से reproduce होने वाले सैकड़ों bugs हैं, लेकिन किसी ने debug नहीं किया। मुश्किल चीज़ से टकराने से पहले काफी देर तक एक-एक करके काटते जा सकते हैं
    मुझे लगता है यह attitude उस दौर की विरासत जैसा है जब लोग branch target address को इस तरह tune करते थे कि drum head ठीक उस समय पहुँचे जब CPU को instruction चाहिए। जब resources बेहद constrained थे, सब कुछ हाथ से assembly में लिखा जाता था, और global memory locations का मतलब program stage के हिसाब से बदलता था, तब बहुत smart लोग पहले से ही performance को critically देखते थे, इसलिए वही चीज़ ढूँढनी पड़ती थी जो वे नहीं ढूँढ पाए। modern code में यह rare है

    • broadly सहमत हूँ, लेकिन bugs को divide-and-conquer strategy से track करना कहीं आसान होता है
      अगर request X को service Y पर भेजने से bug reproduce होता है, तो culprit मिलने तक test case को लगातार छोटा करते जाइए
      optimization अक्सर architecture issue होता है। कभी-कभी buffer reuse हो सकता है लेकिन copy हो रही होती है, पर ऐसी चीजें जल्दी खत्म हो जाती हैं, और profiler जरूरी information बता देता है
      बड़े performance gains अक्सर पूरे data flow को बदलने, और significant हिस्से हटाकर code से जरूरी काम को जितने कम steps में हो सके करवाने से आते हैं
  • जिज्ञासा है कि key-value store की जगह SQLite क्यों चुना। लगता है सिर्फ ID से read करना है और दूसरे columns की जरूरत नहीं, तो relational database unnecessary लगता है

    • ऐसा हो सकता था। MariaDB में temporary table बनाना भी संभव था
      SQLite का फायदा single file होना है। इसलिए इसे copy या share करके कुछ अच्छे काम किए जा सकते हैं
  • अच्छा है कि यह constraints से innovation जन्म लेने का एक और example है। innovation समृद्धि से ज्यादा अक्सर limitations में मिलती है