PSF (Python Software Foundation) po mnoha měsících práce získala grant ve výši 1,5 milionu dolarů od americké vládní NSF (National Science Foundation) v rámci programu "Bezpečnost, ochrana a soukromí open source ekosystémů" na zvýšení bezpečnosti Pythonu a PyPI. PSF ale nesouhlasí s předloženou podmínkou grantu, že během trvání finanční podpory nebude žádným způsobem podporovat diverzitu, rovnost a inkluzi (DEI). PSF má diverzitu přímo ve svém poslání (Mission) a proto grant odmítla.
Balík nástrojů Rust Coreutils / uutils coreutils, tj. nástrojů z GNU Coreutils napsaných v programovacím jazyce Rust, byl vydán ve verzi 0.3.0. Z 634 testů kompatibility Rust Coreutils s GNU Coreutils bylo úspěšných 532, tj. 83,91 %. V Ubuntu 25.10 se již používá Rust Coreutils místo GNU Coreutils, což může přinášet problémy, viz například nefunkční automatická aktualizace.
Od 3. listopadu 2025 budou muset nová rozšíření Firefoxu specifikovat, zda shromažďují nebo sdílejí osobní údaje. Po všech rozšířeních to bude vyžadováno někdy v první polovině roku 2026. Tyto informace se zobrazí uživateli, když začne instalovat rozšíření, spolu s veškerými oprávněními, která rozšíření požaduje.
Jste nuceni pracovat s Linuxem? Chybí vám pohodlí, které vám poskytoval Microsoft, když vás špehoval a sledoval všechno, co děláte? Nebojte se. Recall for Linux vám vrátí všechny skvělé funkce Windows Recall, které vám chyběly.
Společnost Fre(i)e Software oznámila, že má budget na práci na Debianu pro tablety s cílem jeho vyžívání pro vzdělávací účely. Jako uživatelské prostředí bude použito Lomiri.
Proběhla hackerská soutěž Pwn2Own Ireland 2025. Celkově bylo vyplaceno 1 024 750 dolarů za 73 unikátních zranitelností nultého dne (0-day). Vítězný Summoning Team si odnesl 187 500 dolarů. Shrnutí po jednotlivých dnech na blogu Zero Day Initiative (1. den, 2. den a 3. den) a na YouTube.
Byl publikován říjnový přehled dění a novinek z vývoje Asahi Linuxu, tj. Linuxu pro Apple Silicon. Pracuje se na podpoře M3. Zanedlouho vyjde Fedora Asahi Remix 43. Vývojáře lze podpořit na Open Collective a GitHub Sponsors.
Iniciativa Open Device Partnership (ODP) nedávno představila projekt Patina. Jedná se o implementaci UEFI firmwaru v Rustu. Vývoj probíhá na GitHubu. Zdrojové kódy jsou k dispozici pod licencí Apache 2.0. Nejnovější verze Patiny je 13.0.0.
Obrovská poptávka po plynových turbínách zapříčinila, že datová centra začala používat v generátorech dodávajících energii pro provoz AI staré dobré proudové letecké motory, konvertované na plyn. Jejich výhodou je, že jsou menší, lehčí a lépe udržovatelné než jejich průmyslové protějšky. Proto jsou ideální pro dočasné nebo mobilní použití.
Typst byl vydán ve verzi 0.14. Jedná se o rozšiřitelný značkovací jazyk a překladač pro vytváření dokumentů včetně odborných textů s matematickými vzorci, diagramy či bibliografií.
Tiskni
Sdílej:
#ifndef SORTING_H #define SORTING_H char **alloclines(int n); char **realloclines(char** memold, int *nold); int cmp(char *s1, char *s2); int readline(char *l); void freelines(char **l, int n); void print(char **l, int n); #endifSprav, nech načítava ne do prázdneho riadku, ale dokiaľ je vstup. Vstup ukončíš v konzole CTRL + D. ...
if(fgets(...) == NULL)
{
// vstup bol ukončený
}
A funkciu main dávaj nakoniec v súbore (alebo najdôležitejšiu funkciu, ak tam nie je main v zdrojovom kóde). Taký nejaký profesionálnejší štandard.
A ďalšia poznámka. Neplytvaj pamäťou. Tj. alokuj pamäť na riadok, až keď budeš mať riadok načítaný. Vtedy vieš jeho veľkosť, a miesto MAXLINE alokuješ reálnu veľkosť.
A použi štruktúru (dátový typ), popíš ňou riadky a s ňou pracuj. A aj tú daj na spracovanie funkciám ako parameter. To potom bude krása.
A keď chceš profesionálnejšie, tak aj testuj stupy pre funkcie. Chyba je NULL, a co ak všade pošlem napr. pre char **realloclines(char** memold, int *nold) ako memold NULL alebo *NULL;
.h soubor pouze pro main.c opravdu moc nemá moc smysl. .h soubor má smysl, pokud ho bude někdo includovat, nejlépe více souborů než jen main.c
Tvoj program skoro robí ako príkazy # cat | sortIf you hold a UNIX shell up against your ear. Can you hear the C? :-)
Tvoj program skoro robí ako príkazy # cat | sort A ďalšia poznámka. Neplytvaj pamäťou. Tj. alokuj pamäť na riadok, až keď budeš mať riadok načítaný. Vtedy vieš jeho veľkosť, a miesto MAXLINE alokuješ reálnu veľkosť.Jednoduché řešení je mít samostatný buffer pro vstup a v okamžiku, kdy je řádek načtený, tak ho vykopírovat na čílové místo něčím na způsob
strdup(), takže se použije jen tolik paměti, co je třeba. Onen vstupní buffer může být ve většině případů dokonce staticky alokovaný, případně dynamicky alokovaný na určitou předem nastavenou velikost, protože pokud nepotřebujeme neomezeně dlouhé řádky, je jednodušší řešení nesmyslně dlouhé řádky zahazovat (k čemu je např. konfugurační soubor, z jehož čtení nám půjdou oči šejderm a při jehož editaci se uscrollujeme k smrti
) .
No a pokud je třeba dynamická alokace, tak nemá smysl zvyšovat velikosti po jednotkách byte, minimální granularita většiny implementací hald je většinou kolem šestnácti byte a pokud se paměť opravdu přidává, tak je to minimálně o velikosti jedné stránky (4KB na x86 a běžných ARMech, dá se zjistit dynamicky přes getpagesize() nebo sysconf()). Když už, tak zvětšovat právě o velikost stránky nebo něco strovnatelného.
Mimo toho, že se ušetří čas, kderý by se zbytečně trávil managementem haldy (bez toho, že by zavolal sbrk()), to má vliv i na nižší fragmentaci haldy, obzvlášť pro pesimální případy, kde délka řádku monotóně roste s jeho pozicí (takže nelze znovu použít uvolněné "díry" v haldě).
PS: Když se toto alokuje opravdu, ale opravdu hodně (IIRC, limit je 128MB u GNU libc), tak malloc() a spol. začnou požívat místo haldy přímé mapování anonymní paměti pčes mmap() (tedy, v unixech, jask se to dělá ve Windows, nemám potuchy). Osobně si myslím, že pak je lepší se na paměťový management přes malloc() a spol. vykvajznout a buď použít nějaký lepší alokátor, nebo si to dělat ručně právě přes malloc(), což má navíc výhodu v tom, že můžeme mnohem přesněji ovlivnit, jak se s pamětí nakládá (přes madvise())nebo kdy se paměť uvolní (nutné, když jednu chvíli potřebujeme spoustu paměti a v té náskledujcí jí musíme zase uvolnit pro někoho jiného).
IIRC, limit je 128MB u GNU libcMoje mallopt(3) říká, že ten limit je 128 KiB.
tak malloc() a spol. začnou požívat místo haldy přímé mapování anonymní paměti pčes mmap()Python (resp. CPython) dělá něco takového taky. Debugování memory leaků je pak výborný :-/
>>> import kerberos
>>> kerberos.authGSSClientInit("HTTP@krbhost.example.com")
(1, <PyCObject object at 0x7f56004e65d0>)
>>>
Ano, muze za to kerberos modul napsany v C, ale hadam ze debugovani python C extensions mel prave kralyk na mysli.
Měmory leak v Pythonu? Wtf?Python-C interop. Céčková strana naalokuje nějaké pythonní objekty a neuvolní je. Tyhle objekty můžou bejt naalokovaný přes malloc, ale někdy taky přes mmap (zcela bez volání mallocu). Nástroje jako valgrind a podobně tohle nedohledají. Nakonec jsem to řešil trasováním mmap syscallu a koukal na backtraces, abych zjistil, odkud se to alokuje. Možná existuje chytřejší způsob.
Jasně. Jak výše vyplynulo, leakuje nějakej c bazmek, ale může za to Python.Tenhle čistě pythonní kód u mě sežere ~1GB RAM:
#!/usr/bin/env python2
import sys
class Foo(object):
def __init__(self, other=None):
self.other = other
def __del__(self):
pass
if __name__ == "__main__":
for i in range(1000000):
foo = Foo()
bar = Foo(foo)
baz = Foo(bar)
foo.other = baz
sys.stdin.readline()
(V Pythonu 3 mi to nejde reprodukovat, proto then python2)
Jinak ale leaky jdou vytvořit i bez triků s __del__, viz třeba tenhle kód:
#!/usr/bin/env python3
import sys
foobar = []
def avg_line_length(file):
avg = len(file.readline())
if avg == 0:
return 0
else:
avg -= 1
n = 1
for line in file:
n += 1
avg = avg + (len(line) - 1 - avg) / n
foobar.append(line)
return avg
if __name__ == "__main__":
print(avg_line_length(sys.stdin))
sys.stdin.readline()
Tady je sice hodně zřejmý, kde a proč to leakuje, ale jakmile budeš mít nějakou větší codebase ve který bude podobný problém zašmodrchaný a rozetřený přes X modulů, už nebude tak snadný to dohledat.
Tož tak.
Já tomu python3 kódu moc nerozumím, ale za ten leak považuješ ten foobar?Jj. Kvůli němu má ten program lineární paměťovou složitost místo konstantní.
foobar v tom prográmku výše není k ničemu potřeba, ale GC to nepozná. Být to v nějakém jazyce s nějakým chytrým kompilátorem, mohl bys dostat warning, něco jako "Value assigned to foobar is never used" nebo podobně...
A ano, to, jestli program nějaký resource potřebuje, může být věc názoru. Např. v některých C/C++/apod. programech jsou objekty, který se jednou naalokujou a záměrně nikdy neuvolní. Valgrind to může označit za leak, ale přitom programátor to za leak nepovažuje.
Být to v nějakém jazyce s nějakým chytrým kompilátorem, mohl bys dostat warning, něco jako "Value assigned to foobar is never used" nebo podobně...Nevím, jak u pole, ale u obecného objektu dost těžko – máš totiž nějakou instanci a na ní voláš nějakou metodu (
append) a jestli tu instanci pak někam přiřadíš nebo s ní uděláš něco jiného je jedno – ta užitečnost mohla spočívat v tom, že jsi volal tu metodu a instance na základě toho něco dělala.
leakuje nějakej c bazmek, ale může za to Python.Za leak může C bazmek, to je bez debat. Za to, že ten leak šel blbě dohledat nicméně může CPython, protože se snaží bejt chytrej a používat vlastní alokační fígle s
mmap(). Jak moc jsou tyhle fígle užitečný, to nevim, možná jsou, ale mám svoje pochybnosti...
int pro účel velikosti něčeho v paměti. Velikost toho typu může být nedostatečná, nebo naopak příliš velká. Používej typ size_t. Funkce jako malloc, calloc, realloc, všechny mají parametr typu size_t. Funkce qsort taky očekává parametry typu size_t. Používáním intu se můžeš dopustit závažných chyb, např. přetečení a následné předání špatné velikosti daným funkcí, kvůli konverzím.
2) Pokud funkce realloc selže, původní buffer není uvolněn. Máš tam možný memory leak ... sice hned voláš exit(), ale může tě to naučit špatným zvyklostem, třeba až takovou kontrolu někdy dáš do nějaké vlastní knihovny, co ukončovat program nebude.
3) Komparátor funkce qsort má typ int (*)(const void *, const void*). Tvůj má úplně jinou signaturu. To přetypování je hnus, nejsem si jistý, ale asi se dokonce bude jednat i o UB, teoreticky by ty funkce nemusely být volatelné stejným způsobem. A obzvláště, když v tom komparátoru stejně přetypováváš, tak můžeš nechat signaturu správně.
4) Dynamická alokace je většinou od toho, abys nemusel mít nějaký fixně veliký buffer, což stejně pro jednotlivé řádky máš. Jednotlivé řádky bych alokoval až poté, co ho přečteš.
5) Asi je zbytečné mít extra funkci pro realokaci, funkci realloc můžeš předat NULL jako první parametr a bude se chovat jako malloc. Stačí inicializovat proměnnou předem na NULL a nemusíš pak mít 2 funkce, co dělají to samé.
6) Ukazatele (kromě ukazatelů na funkce) jsou implicitně přetypovatelné na void*, netřeba přetypovávat, pokud voláš funkci free(). void* ukazatele jsou implicitně přetypovatelné na ukazatele na jiné (platí pouze v C, v C++ to neplatní).