Trillian Pro – No Buffer Space Available

I tried to post this in the technical support forum, but I do not have enough privileges, so I thought until the moderators verify me I will post this here:

First of: Trillian have not displayed any error messages. So I had to track it down.

Symptom:
One of my program was unable to connect to a server and logged the “No buffer space available.” error.
Then checked with IE, it was unable to open web pages either.
This error made all application on my pc unable to connect to anywhere (new).

Track, hunt, kill:
This was not the first time I came across this kind of problem in the past. So I run
‘netstat -n -o’ to identify the problem and the process involved. It was Trillian.exe.
When I shut it down (Exit) it did not terminate in a timely fashion, so after half a minute I had to kill the process manually form task manager.
After it finally terminated everything went back to normal and worked again.

I’m not sure which service caused the problem, Twitter is just a guess from the IP addresses, but might be completely wrong…

Other problems:
By the way Trillian used a lot of memory. (it went from 30 MB working set at strartup to around 300MB after a couple of weeks uptime)
So there is some “memory leak” in it… (it might be just caching a lot of pictures or something)

Here is the relevant part of netstat result:
TCP 192.my.ip.addr:49157 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49158 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49159 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49160 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49161 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49162 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49163 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49164 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49165 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49166 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49167 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49168 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49169 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49170 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49171 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49172 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49173 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49174 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49175 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49176 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49177 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49178 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49179 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49180 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49181 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49182 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49183 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49184 199.16.156.8:443 CLOSE_WAIT 292

TCP 192.my.ip.addr:49913 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49914 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49915 199.16.156.104:443 ESTABLISHED 292
TCP 192.my.ip.addr:49916 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:49917 199.16.156.104:443 CLOSE_WAIT 292

TCP 192.my.ip.addr:50642 199.16.156.231:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:50643 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:50644 199.16.156.8:443 ESTABLISHED 292
TCP 192.my.ip.addr:50645 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:50646 199.16.156.8:443 CLOSE_WAIT 292

TCP 192.my.ip.addr:51665 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:51666 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:51667 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:51668 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:51669 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:51670 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:51671 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:51672 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:51673 199.16.156.104:443 CLOSE_WAIT 292

TCP 192.my.ip.addr:52136 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52137 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52138 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52139 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52140 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:52141 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52142 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52143 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52144 199.16.156.40:443 CLOSE_WAIT 292

TCP 192.my.ip.addr:52583 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52584 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52585 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52586 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52587 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52588 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52589 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52590 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52591 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52592 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:52593 199.16.156.199:443 ESTABLISHED 292
TCP 192.my.ip.addr:52594 199.16.156.40:443 CLOSE_WAIT 292

TCP 192.my.ip.addr:53297 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53298 199.16.156.104:443 ESTABLISHED 292
TCP 192.my.ip.addr:53299 199.16.156.8:443 CLOSE_WAIT 292

TCP 192.my.ip.addr:53661 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53662 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53663 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53664 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53665 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53666 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53667 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53668 199.16.156.199:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53669 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53670 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53671 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53672 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53673 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53674 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53675 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53676 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53677 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53678 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53679 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53680 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53681 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53682 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53683 199.16.156.72:443 ESTABLISHED 292
TCP 192.my.ip.addr:53684 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:53685 199.16.156.72:443 CLOSE_WAIT 292

TCP 192.my.ip.addr:54854 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54855 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54856 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54857 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54858 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54859 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54860 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54861 199.16.156.231:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54862 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54863 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54864 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54865 199.16.156.72:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54866 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54867 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54868 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54869 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54870 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54871 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54872 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54873 199.16.156.40:443 ESTABLISHED 292
TCP 192.my.ip.addr:54874 199.16.156.104:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:54875 199.16.156.72:443 CLOSE_WAIT 292

TCP 192.my.ip.addr:65533 199.16.156.40:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:65534 199.16.156.8:443 CLOSE_WAIT 292
TCP 192.my.ip.addr:65535 199.16.156.40:443 CLOSE_WAIT 292

16351 connection from this one process

Trillian Version: 5.3 Build 16 Pro June 13, 2013

Reuse sockets maybe!?

Google Drive Resync

I just reinstalled my OS and I’m reinstalling applications. One of which is Google Drive. After installing it, I signed in, and proceeded to choose my old Google Drive folder but it would not let me. Saying “Google Drive Folder you selected is not empty, please select an empty folder”. Searching for solutions I found that there is none and I have to re-download everything from cloud storage into an empty folder.
http://productforums.google.com/forum/#!topic/drive/pRWtrdhUjuE%5B1-25-true%5D

*note: Installing Drive to a new hard disk, reformats, or image restores will require a new empty folder to be created and set as the sync directory. This is not a program error but is part of its design.

Maybe someone could redesign it then? It’s really inefficient to re-download everything.
I can’t believe Google Drive cannot figure this out. Dropbox did not have any problem, just re-indexed the files. I can also force re-check even unfinished torrent files, so it’s not that hard to check file name, size, hash matches…

I see this trend happening with Google’s software: getting more shiny and dumber, features and settings getting removed. I guess that’s what happens when you don’t pay for it: “Don’t look a gift horse in the mouth.”

By the way I always design my software to randomly crash, they are not program errors 🙂

Also Google Drive installer should not kill (and restart) explorer.exe, it’s really f*@#ing rude!

Otherwise I like Google, they are providing us with some really fine free products, but I don’t think I will want to convince anyone to buy extra storage space from Google, because the initial syncs of a couple 100 GBs would make us tear our hair out pretty soon, and that is not a good look for me…

dynamic arrays and the lack of them in C

I love Pascal and Delphi. In particular I love its memory management.
I can use string, array of byte types. They are both dynamic arrays. They are not just pointers to a memory region, they have a size or Length (how Delphi calls them).
The great thing about them is that they can be re-sized. But an other great thing is that you can check their sizes no matter what (if you forgot to remember them, or if you receive them as argument of a function/procedure/method).
SetLength()
Length()
Low()
High()
Open array parameters
^^^^ This is what I need in C!

In C it’s like they want to hide this information from you. First, there is no such thing as dynamic array in C (there are only pointers). There are arrays in C++ (but I read that you should avoid them at all cost, and use vector instead), but also you cannot re-size them, so they are not fixed length, but not really dynamic either.
So how can you get the length of an array or memory region?
common methods:
In C you can use #define lengthof(array) (sizeof(array)/sizeof(array[0])) if it’s a fixed length array, but you cannot use it on function arguments, or pointers…

There is a clever template (if you write it) in C++
template
inline unsigned int length( T(&a)[N] ) { return N; }
that can be used to determine length of arrays.

So where are the real dynamic, realizable arrays, and how to implement them?
If you want to allocate memory run-time (and re-size them) you can use malloc() (realloc() and free())
That’s all fine until you want to get the size of them. Which can happen if you allocate the memory outside of a function where you want to use it. There is no std libc function to get the (malloc) allocated memory size which is kept somewhere (so free() can free it, realloc can re-size it and available memory regions can be kept track of). There is however a GNU extension malloc_usable_size() which I, we desperately need (even if we didn’t know it).
.. Well we need an array whose size we can check no matter if it’s dynamic or static, but…
Also note that malloc_usable_size does NOT actually return the requested size, but the allocated one (due to alignment, minimum block size), but at least we can use it for asserts.
So we still need to keep track of array sizes separately (extra variables, extra arguments) and risk messing them up…
(or rewrite everything to use structures of size, pointer pairs)

Another topic is multidimensional (dynamic) arrays (not just arrays of arrays)…

Note: This actually I have written just now 🙂 See I do not just reuse ages old materials:)

Hungarian notation

Hungarian notation is usually miss-interpreted as the notation of declared type of variable. This is not the case. So when I read a book that says that Hungarian notation is useless in type safe languages, I feel bad. 🙁

Hungarian notation is supposed to indicate semantic type (type of content, meaning) and not syntactical type (type of variable). The compiler knows how to handle (read, write, do operations with) variables, but it has no idea what they are, what they mean. And if you are not naming your variables right you might not either.

Lets say you are writing some physics calculation. You are probably do not want to add mass with length or acceleration… (you might want to multiply, divide them but not add, subtract). To the compiler (even the most type safe ones) they are all just floating point numbers (or doubles, extendeds). And if you are naming your variables like marias_speed, peter_is_this_fast, velocity_of_kevin, then you are looking for trouble. It’s harder to notice the error in this: marias_speed + peter_is_this_fast + mass_of_kevin, than in this: veMaria + vePeter + maKevin. In this case Hungarian notation could mean units of measurement.
The same goes if you are calculating screen position in pixels, inches, centimeters…

The more common task a programmer has to deal with is user input. User input is always unsafe! An SQL string is (or should be) treated differently than user input, or html text… strings need to be escaped differently for different output. So it might be advantageous to include in the variable name if it’s unsafe, html-safe, sql-safe …
Also use printf(“%s”,usStr) rather than printf(usStr) 🙂

Note: I found this old draft from 2012 January. Another one again… I shouldn’t misplace these 🙂

preDict

My smart phone is smarter than my Offices on my PC when it comes to text entry. Somehow MS Office Word and LibreOffice Writer just have not kept up. They are smarter than a typewriter (and sometimes spell better than me… well most of the times they do : ), but not as smart as they could be. Instead of redesigning the user interface every few year, Microsoft should focus on usability features rather than a shiny UI. It’s nice for a few seconds to look at something pretty, but when you are actually working with it, and using it to type in text, than that is what matters the most, and that is what you are looking at (or your keyboard if you are not typing blind). The GUI redesign is also annoying when you have to relearn using it. I’m still sometimes spending more time googling how to do something simple in Word 2007, 2010 (or LibreOffice) than actually doing it (and thinking “I could have already finished this in Word 2003”). Same for Windows 7, 8 vs. XP. But this post is not about that…

This post is about predictive text. Something that my Samsung phone (the virtual keyboard) does pretty well. It’s not perfect, but at least tries. I cannot say the same thing about Office or PC keyboard. We had some kind of predictive text on phones for a while. T-9 dictionaries and typing helpers. But the Text input on the Android based Samsung phone is amazing. (The handwriting recognition is also pretty accurate and faster than typing if you are not jogging or traveling on a bus.) I start typing in a word and it provides a list of guesses (words that start with those characters, or words that might have been mistyped…). It not just does that, but after finishing a word it also guesses words that usually follow the previous. You can almost type an entire sentence just by accepting guesses. Where is this on PC?

Visual Studio has intelli-sense that helps a lot with code writing. Microsoft should implement a form of that in Word. Just exchange dot to space and treat sentences as qualified variable names. (It’s not that simple, but it basically needs to just accept every word in the dictionary and use some probability algorithm to order the suggestions.)
Other IDEs have some kind of code completion too. (Delphi, Eclipse, even Notepad++ and Far manager …)

Here is a predictive text plugin for MS Word to fill this feature hole.
preDict
It’s a good start, but it’s not complete, and Word should support this internally.

There are some other tools that you can use.

You can configure AutoHotkey to fix your commonly miss typed words for example.

There was also Google Scribe. No longer…
AIType won’t let me register…
LetMeType might actually work.

Meggyfa R.I.P.

A héten kidÅ‘lt az egyik meggyfánk 🙁

A hétvégét a fa eltakarításával, illetve a meggy leszedésével töltöttük. Így kicsit egyszerűbb volt a mennyet szedni, nem kellet létrára mászni…
Több mint 50 kg meggyet mértünk le válogatás után, úgy hogy körülbelül a szomszédok is leszedtek ennyit. A másik két meggyfához hozzá se nyúltunk.
A hétvége másik fele a meggy feldolgozásával telt.