Sunday, February 12, 2017

Zkušenosti se Zonky, aneb když jde do tuhého

Pokud se rozhodnete na WWW vyhledávat informace o Zonky, obvykle najdete několik článků představujících uživatelské rozhraní Zonky a základní úkony, případně pak stížnosti těch, kterým Zonky kvůli záznamům v registrech nepůjčilo. Zonky je na světě poměrně krátkou dobu, ale díky televizní reklamě získává hodně pozornosti. To vede k tomu, že ti, kdož se chtějí stát investorem na Zonky, musejí dlouho čekat, než na ně dojde řada. Právě těm, kteří přemýšlejí o zapojení nebo už dokonce čekají, než na ně přijde řada, je tento článek určený.

V první řadě chci říci, že služby jako Zonky se mají stejně jako blízký přítel hodnotit podle toho, jak se chovají v těžkých chvílích. V případě platformy na P2P půjčky jde o situace, kdy dlužník nesplácí nebo jde dokonce do bankrotu...

To dobré...

Na Zonky oceníte to, že na rozdíl od jiných P2P platforem na českém trhu (jako například Bankerat) se snaží filtrovat evidentní trosky s 10 záznamy v registru a stádem exekutorů za zády. Po mých cca osmiměsíčních zkušenostech musím říct, že až na výjimky všichni platí.

Občas někdo platí chronicky o pár dnů pozdě, občas někdo nemá trvalý příkaz nastavený tak, aby dobře reflektoval splatnost o víkendu, ale aspoň za současné ekonomické situace se neděje, že by vám půlka dlužníků přestala po dvou splátkách na dobro platit. Investoři se o rizikovější půjčky dost perou (až z toho chvílemi kolabuje server), ale ani to nevedlo k tomu, aby Zonky otevřelo stavidla a vpustilo na trh hromady pochybných zájemců o půjčky.

Sem tam se sice na tržišti objeví nějaký exot, který si například chce půjčit (s docela vysokým úrokem) na to, aby "bez rizika investoval do čehosi dalšího s jistou návratností 20 % p.a.", ale tam se aspoň ukáže, kdo před investováním studuje, komu ty peníze dává.

Fajn je i to, že Zonky (respektive asi PPF) doinvestovává půjčky, ke kterým se nesehnal dostatek investorů. Toto je problém hlavně půjček s nízkým rizikem (neboli nízkou úrokovou sazbou), vysokou půjčovanou částkou a dlouhou dobou splatnosti. Přece jen není úplně fajn mít někde "zablokované" svoje peníze na dlouhou dobu s velice nízkým výnosem, když nevíte, jak to za pár let bude s inflací. Bez zásahu Zonkyho by tyto žádosti o půjčku zůstaly nezainvestované, paradoxně by tak kvalitní dlužníci neměli šanci dosáhnout na úvěr.

To horší

Zonky má několik stinných stránek. Tou první je kvalita samotného tržiště ve smyslu webové aplikace. Působí příliš jako hračka a trpí nejrůznějšími neduhy či nedodělky. Z historie mohu například zmínit chybu, kdy po údaji o výnosu 7,9 % následovala hodnota 7,10 % (namísto 8,0 ), protože to skript nějak špatně počítal. U finanční instituce je to trochu na pováženou.

Dalším nedostatkem je to, že člověk nemůže snadno zjistit, kolik splátek mu dlužník dluží. Je samozřejmě možné si to nějak dovodit / dopočítat, ale není to vůbec pohodlné. Obecně reporting na tom není dobře, neduhů by se dalo jmenovat povícero.

Pak jsou tu doposud nenaplněné sliby v podobě sekundárního trhu, neboli možnosti svou investici prodat někomu jinému. Aktuálně platí, že když investujete do půjčky se splatností 6 let, tak za 6 let ještě budete muset stále být uživatelem Zonky.

Nepotěší vás ani to, že kdyby Zonky jako takové šlo do bankrotu, pak pohledávky za dlužníky budou přednostně použity k uspokojení věřitelů Zonkyho jako takového (takže třeba PPF). Svými investovanými penězi tedy zajišťujete podnikatelské riziko Zonky s.r.o.

To nejhorší

Největším problémem Zonkyho je nedostatek komunikace. Zonky říká, že od prvního dne, kdy je půjčka po splatnosti, komunikují s dlužníkem. Jenže vy jako investor se z této komunikace nedozvíte vůbec nic.

Zonky dělá maximum pro to, aby chránilo dlužníky, a to i na úkor investorů. Je jasné, že P2P platformy budou plné "plašanů", co se domáhají krve dlužníka, jakmile se opozdí se splátkou o několik dnů, takže Zonky se musí trochu obrnit.

Průšvih je ale v tom, že Zonky maximálně chrání dlužníky i v situaci, kdy dlužník požádá insolvenční soud o oddlužení, a dokonce i v situaci, kdy dlužníkovo počínání zavání úvěrovým podvodem.

Pan učitel

Právě teď komunitou otřásá případ jednoho pana učitele, který si během několika měsíců napůjčoval skoro 1,5 milionu, přičemž jen na Zonky jde celkem o 300 000 Kč ve dvou různých půjčkách. Druhou zmiňovanou půjčku (do které jsem investoval) si vzal v srpnu 2016 a nikdy nezaplatil ani jedinou splátku řádně.

Kontaktoval jsem Zonky, abych se dozvěděl, jak to vypadá, a dostalo se mi poněkud strohé odpovědi, že to vypadá dobře.

No a o pár týdnů později dlužník požádal o osobní bankrot. Měsíc na to Zonky na vzniklou upozornilo dotčené investory e-mailem, podle kterého je vlastně všechno v normě. Smrdět to začne člověku v moment, kdy si uvědomí, že půjčka byla klasifikována jako "A++" (neboli poměrně dobrý rating), přitom ten člověk fakt ani jednou nezaplatil řádně.

Komunita investorů (která se schází na Facebooku) se začala pídit po detailech. Zonky nám nechtělo o insolvenci prozradit podrobnosti, naštěstí se ale rychle podařilo najít daný případ v Insolvenčním rejstříku. Reakcí Zonky bylo to, že se spojilo se správcem dané facebookové skupiny a veškteré komentáře identifikující dlužníka (tedy ty s odkazem na veřejné informace v Insolvenčním rejstříku) jsou mazány.

Po přečtení návrhu na povolení oddlužení a všech příloh člověk dospěje k několika závěrům:

  • Dotyčný si docela rychle napůjčoval velké peníze. Nebylo to ale dost rychle na to, aby dle mého názoru Zonky nemohlo dané údaje najít v registru.
  • Přestože si napůjčoval tolik peněz, tak nemá vpodstatě žádný zpeněžitelný majetek. Řečeno jinými slovy ty peníze někam ulil.
  • Přestože se vymlouvá na to, že v nové práci vydělává míň peněz, prostým součtem lze dospět k závěru, že by půjčky nezvládal platit, ani kdyby zůstal ve staré práci.
  • Dlužník tedy buď nesdělil Zonky úplné informace o svých závazcích, nebo je Zonky špatně vyhodnotilo. Znovu připomínám, že mu Zonky dalo rating A++, nikoliv nějaké D.
  • V době, kdy mu byl načerpán druhý úvěr u Zonky, už byl nezaměstnaný, protože mu skončilo předchozí zaměstnání na dobu určitou.
  • Tak jako tak si dlužník musel být v době načerpání druhého úvěru u Zonky vědom toho, že nebude schopen splácet.

Pokud vás zajímají podrobnosti, tak si přečtěte odkazovaný spis u Insolvenčního soudu. Zjednodušeně řečeno to celé dost smrdí úvěrovým podvodem. Pokud vám to přijde v pořádku, tak si na to vzpomeňte, až si sami budete brát úvěr - ano, ta procenta jsou tak vysoká, abyste zatáhli dluhy i za ty, kterým bylo povoleno oddlužení. A vězte, že v ČR se schvaluje oddlužení i odsouzeným úvěrovým podvodníkům. Bohužel.

Pan učitel si to spočítal moc dobře. Napůjčoval si fůru peněz (otázkou je, proč mu vlastně bylo tak ochotně půjčováno?) a za necelé čtyři měsíce od podpisu posledního úvěru vstupuje do insolvence, kde navrhuje, že splatí jen třetinu jistiny. To je docela fajn, ne?

Na Facebooku se pak objevuje vyjádření:

Přeložená verze: Zonky chce, aby se lidé, kteří si půjčují na Zonky, cítili v bezpečí. I když vypadají jako podvodníci. A když se na Zonky nebudou podvodníci cítit v bezpečí, tak přece nebudete mít do koho investovat...

Neoficiálními kanály se pak dozvídáme, že jsou si v Zonky vědomi, že minimálně ten poslední úvěr smrdí podvodem, právníci jim ale doporučili nechat to plavat, protože takhle je prý větší šance, že dotyčný aspoň něco zaplatí. Se záznamem v trestním rejstříku je totiž nemožné dělat učitele.

Pro mě, jakožto osobu, která investovala 200 Kč, je ale důležitější spravedlnost než to, abych dostal zpátky 47 Kč (34 %, které dlužník slibuje splatit, mínus 30 % provize Zonky za "vymožení" dlužných peněz). Raději uvidím pana učitele jako bezdomovce pod mostem, než aby takový zlořád učil naše děti a procházelo mu to. Proto jsem na něj podal trestní oznámení.

Mnoho lidí lidí v tento moment řekne, že u P2P půjček musí člověk s bankroty počítat. Něco jiného je ale bankrot u člověka, který se životními komplikacemi dostane do nesnází, a bankrot u člověka, který před rokem nedlužil nic, napůjčoval si pochybným způsobem horu peněz, peníze někomu dal a teď slibuje, že vrátí třetinu.

A nejhorší je na celé věci přístup Zonky, které buď mlčí nebo mlží nebo se ještě dlužníka zastává.

Závěr

Zonky nemusí být špatná platforma, bohužel je dost znát, že se jedná o startup, nikoliv o profesionální a zavedenou službu, s jakými je možné se setkat v zahraničí. Tam bývá běžné, že v případě defaultu dostávají investoři veškeré informace.

Nechci vás odrazovat od toho, abyste se stali investory. Určitě bych vám ale nedoporučil, abyste do Zonkyho investovali nějaký výrazně větší podíl vašich volných prostředků.

Saturday, February 4, 2017

Running 32-bit code in 64-bit Linux processes

This article is about some very low-level stuff. If you are interested in loading 32-bit libraries in 64-bit applications, then go away - this is not the kind of stuff you are looking for.

While working on improving Darling, I started looking for a way of executing 32-bit macOS software bootstrapped in a 64-bit Linux process. This approach has certain advantages, but also brings some complications. As of writing this article, it is still an emerging technology developed in a branch.

The primary property of the 32-bit code is that it's fully self-contained. It makes system calls on its own and it won't be until a lot later until it needs to interface with 64-bit ELF Linux libraries.

How I Started

In the beginning, I thought I could execute 32-bit code directly, because every 64-bit process can make 32-bit system calls on Linux. The only complication was allocating a new stack at an address reachable from 32-bit code (= somewhere in the first 4 GB of process memory).

But I quickly learned that some instructions behave differently when executed as 64-bit. For example, the following two instructions compile to the same opcodes when compiled as 32 and 64 bit respectively, i.e. there is no 64-bit prefix commonly seen in other instructions (such as 0x48).

pushl %ebx
pushq %rbx

This means the CPU must somehow be told to run in 32-bit mode.

How I Made it Work

The Linux kernel maintains various segment descriptors in its GDT. Even though Linux uses pagination (and not segmentation) for memory management, a few segments must still exist for things to work.

The trick is to jump into the 32-bit code and switch the segment selector at the same time. For code, the numbers to remember are 0x23 for 32-bit code and 0x33 for 64-bit code.

// This code assumes %eax contains 32-bit code's address in memory.
subq $8, %rsp
movl $0x23, 4(%rsp)
movl %eax, (%rsp)
lret // long return will pop the address and segment selector

You'll quickly notice your 32-bit code will now execute properly, except it will segfault on any memory access. To make things even more confusing, Linux will report 0 as the faulting address.

The explanation is simple. When the CPU runs in long mode (64-bit), the value of the DS register is forced to 0. The register is not considered for memory access. This is, however, not the case in 32-bit mode. Therefore, we need to set a correct value into DS. As DS is inaccessible in 64-bit mode, the following instructions need to be executed after switching into 32-bit mode.

push $0x2b
pop %ds

Now your code should start running... until it starts making system calls.

System Call Quirks

SYSENTER

If your code makes (32-bit) system calls using the SYSENTER, you will quickly learn that after the system call is executed, the kernel jumps into the middle of nowhere, even if you are certain your code works fine when run in a 32-bit process.

The reason lies within the main deficiency of SYSENTER: it does not save original EIP where to return after the call is finished. This is normally not a problem, because the kernel will jump into a helper function inside of vDSO, which picks up the original EIP from the stack (where your code has stored it).

This will not work now, though, as your process only has a 64-bit vDSO. The solution is to perform system calls by executing the traditional int $0x80.

mmap

The problem with mmap (and mmap2) is funny. The IA32 system call wrapper takes care of extending arguments etc., but a common mmap implementation is eventually called. Unless you set MAP_FIXED, this implementation checks if the process is 32-bit, and if it is, it makes sure the mapping is created in an address range accessible to a 32-bit process.

However, since our process is 64-bit, new mappings will probably get created above the 2^32 limit, the IA32 system call wrapper will cut off the upper 32 bits and your code will receive an incomplete address. The strace output will look very confusing, as strace will show you have successfully created a mapping at an address, but you will probably end up crashing accessing that very address shortly thereafter.

There is a simple fix. Just add MAP_32BIT into the flags for mmap/mmap2. The flag's name is unfortunately not very fitting, I would personally call it MAP_30BIT. The man page says the mapping will be created within the first 2 GB of memory space (What is 32-bit about that? This is only 31 bits!). But it gets worse. If you check the kernel source code, you will notice the kernel also places a lower limit of 0x40000000 on the mapping, which effectively limits the mappings in the range between 0x40000000 and 0x80000000. That's only 30 bits (1 GB) of memory!

So I searched for a different solution. A nice way would be to use personality() and set flags ADDR_LIMIT_32BIT or ADDR_LIMIT_3GB. Sadly, neither of these flags have any effect at all. The whole personality() system call is a bad joke: it only takes effect across execve() and most flags are not implemented.

Alas, the same guy who created the very broken MAP_32BIT is also the guy standing in the way of fixing these flags.