Tuesday, December 31, 2019

Solving inheritance ambiguity with composition

Let's say you have the following C++ classes, making use of the observer pattern:

In implementation of class A, you call Notify(T) of CObservable.

When you compile, you will get a message that there is ambiguity in calling Notify(), because the compiler does not know if it should call Notify(T) with class T1 as a parameter or T2.

The solution is to remove CObservable from inherited classes and introduce a field, i.e. using composition over inheritance. You also need to have a registerT2Observer() method that in turn calls the register method of CObservable:

Letters to a novice programmer

Dear novice, this time it has been a short while, isn't it? When you have a dll that you call from both a Java app and C++ app with the same inputs but the outputs differ, do not suspect that there might be something wrong with the operating system or JNI. Your problems will always be due to something you did wrong.

You should write some debug code inside the C++ dll that prints dll inputs to a file. Run the dll from Java and C++ and compare dll inputs. I guarantee you that you will see a difference there because most probably you did something wrong before passing the inputs to dll like using a wrong index or making an erroneous unit conversion.

Another tip: When comparing files, never trust your eyes, always use a comparison tool like Total Commander's "Compare by content" or Beyond Compare.

Thursday, December 26, 2019

Letters to a novice programmer

Dear novice, it has been a while since my last letter. Today I want to stress the importance of revisiting your code every couple of months or so and asking yourself "could I achieve the same functionality with less code?". In other words, be your own garbage collector. If you do this a couple of times, your code might graduate from being miserable to being tolerable. And who knows, one day it might even attain the coveted status of being "elegant"?

Today's example concerns avoiding unnecessary local variables to reduce clutter:

Wednesday, December 25, 2019

Lessons from teaching my kid math for 10 months with Khan Academy

I have been teaching my 7 year old child mathematics with Khan Academy since February 2019. Everyday at about 19:00, we have a 15 minute session. Right now we are at 85% of 4th grade. During this time, I discovered that the difficulty of math does not lie in concepts, but in the high degree of attention it requires. Contrast a reading assignment with a math problem; In reading, you might omit a few letters, even words and still get the essence of the text and be able to answer questions correctly. With a math problem, if you misread even one symbol, you will be completely wrong. In this respect, math resembles software development.

During our problem solving sessions, I saw again and again that my son had no problem with the subject matter but was usually missing a bit and getting the answer wrong. When I helped him just a little by telling him to be more careful, he was able to solve most of the problems.

I suspect many students who are bad at math struggle due to a lack of attention. Unfortunately, improving attention requires one on one care, which the education system cannot provide. Parents have to help their kids.

Other lessons learnt:
  1. It is frustrating to witness that your child forgets the math rule you explained a minute ago. Be patient and repeat as much as necessary.
  2. Only advance to the next subject when your child can solve all of the end of chapter questions without any assistance from you. You might be dismayed by how many times he might have to repeat that test. As an example, my child solved all 18 questions of Understanding Decimals unit test in one sitting on his 13th try. It took him almost two weeks of frustration and tears! This sharpened his attention and cured his false sense of self-confidence(!)
  3. Every couple of months, revisit older subjects by re-solving their unit tests.
  4. My son is impatient and wants to solve problems quickly in his head. This works for simple operations but once you get to problems involving multiple steps like 12*17, you have to force him to use pencil and paper and show each step clearly to you.
  5. Since every child is different (and also rapidly changes with time), progress and tactics will be different. You have to constantly observe and adapt to the learning/teaching challenges you and your child will face.
  6. Persistence is key and the hardest part. It is easy to teach a couple of times, but most parents struggle to do it consistently.
How am I able to keep him marching on through this difficult journey? First, I have earned his respect and trust by being useful to him in subjects he cares about like video games, internet and sports. Second, I do not refrain from punishing him by reducing his video game time if he gets out of line.

Music: Chumbawamba - Tubthumping

Tuesday, October 22, 2019

The myth of developer independent systems

Today a colleague of mine was asserting that the core reason of sloppy development is not having detailed quality procedures, i.e. bureaucratic systems independent of who is following them. I told him that we have more than enough development procedures, that any complex system is always dependent on the quality of people who implement them. If a project is sufficiently complicated and there is time pressure and market competition, you need high quality people who can evaluate risks realistically, tailor standards and cut corners to save time and effort. But they are also acutely aware of technical debt and clean up the quick and dirty solutions when time permits it.

You never have enough resources to develop your ideal system and always have to settle on a viable product. If your chief engineers are not wise enough, they will underestimate complexity, confuse priorities and take unreasonable risks. The problem is that they won't know that those risks are high. For them it will look like a brilliant course of action, until disaster strikes. If they are bad enough, they won't even be able to learn the correct lessons from failure.

Bad products are not the result of bad procedures but bad engineers and managers. The shortest path to success is to find and nurture good people who can develop quality products, write realistic procedures and make the team better.

Letters to a novice programmer: Content priority

It has been a long time since our last letter. Today I would like to talk about prioritizing content. When writing code or documenting a complex (more than 1 man*month of effort) project, you should always start with high priority features/content first. For example, if you are writing a developer handbook for a piece software, start with the most frequent use case first. Do not write page after page about design details that are not important for that particular use case. You will NEVER have enough time to write about everything you think is necessary. By documenting/coding high priority items, you maximize document/software usefulness.

Monday, October 21, 2019

Sokak köpekleri

Başıboş sokak köpekleri tartışmaları genellikle hayvan sevmek / sevmemek boyutuna indirgeniyor, köpekler konusunda kaygı belirtenler hayvan sevmemekle suçlanıyor. Sokak köpeklerini besleyenlerin şu hususları akıllarında bulundurmalarında yarar var:
  • Köpekler alan koruma ve genişletme içgüdüsü olan hayvanlar, sürü/çete halinde dolaşıyorlar ve iriler. Onların alanından geçerseniz sizi en azından havlayarak tehdit ederler. Bir tanesiyle baş edebilirsiniz belki ama beş on tanesi birden gelirse, kadın çocuk veya yaşlıysanız size kolaylıklar dilerim. Kedilerde bu sorun yok çünkü hem küçükler, hem çeteleşmiyorlar hem de köpekler gibi alan korumaları yok.
  • Evinde köpek besleyenlerin köpeklerini sokakta gezdirmesi stresli bir faaliyet, çünkü başıboş köpekler yabancı köpeklere alerjiktir.
  • Yurt dışında, özellikle Almanya ve Amerika'da uzun zaman geçirdim, sokakta bir tane başıboş köpek görmedim. Onların bizden daha az hayvan sever olduğunu iddia etmek zor.
  • Köpeklerin yola fırlamasından dolayı trafikte kaza riski oluşuyor, daha bu sabah servisimiz bir köpeğe çarptı, az kalsın başka bir arabaya da çarpıyorduk.
  • Köpek tarafından ısırılırsanız 30 gün boyunca uzman bir sağlık merkezine giderek kuduz aşısı olmanız gerekir. Köpek ısırmaları köpeklerin sayısındaki muazzam artışla epey artmış durumda.
  • Köpekten korkan, köpek oynamak niyetiyle dahi olsan kendisine koşup havladığında paniğe kapılan çok insan var, özellikle kadınlar ve çocuklar. Bu insanlara "korkma canım" demek, köpek davranış uzmanı olmasını beklemek haksızlık. Köpek nedeniyle panikleyip düşen, kolunu bacağını kıran iki kişiyi şahsen tanıyorum, aradan bir yıl geçtiği halde hala ağrı çekiyorlar. Köpek korkuları daha da artmış durumda.
  • Bir tanıdığım geceleri sürekli havlayan köpekler nedeniyle uyuyamaz hale geldi ve taşınmayı düşünüyor.
  • Yedi yaşındaki oğlumun beş dakika mesafedeki okuluna yürüyerek gitmesine izin veremiyorum çünkü sokakta köpek olabiliyor. Çocuğumun kendi başının çaresine bakabilen bir insan haline gelmesini mecburen kısıtlamak zorunda kalıyorum.
  • Gözümüz gibi sakındığımız, travma yaşar diye sesimizi yükseltmekten çekindiğimiz çocuklarımıza köpeklerin saldırdığını bir düşünün, ebeveyn olarak ne hissedersiniz? Saldırı olasılığı düşük diyebilirsiniz ancak son derece olumsuz sonuçların yaşanması için bir kez olması yeter. Bir ebeveyn bunu göze alamaz.
  • Sabahları bisiklete binmek, koşmak gibi aktiviteleri unutun, şehirlerimiz tamamen köpek işgali altında.
Şehirlerde giderek artmakta olan köpek nüfusu ciddi bir sağlık ve güvenlik tehdidi oluşturuyor. Sokak köpeklerini besleyenlerin niyetlerinin halis olduğundan şüphem yok ama neye katkıda bulunduklarını da bilmeleri gerek.

When (Several) Dogs Attack

Wednesday, October 09, 2019

Get SVN revision and write to header file

I am creating a C++ dll file from a MATLAB Simulink model. The simulink model repository is hosted on subversion. I needed a way to embed simulink model subversion revision to dll so that the dll could return that revision via an interface method to interested clients. I wrote the following batch file to fetch revision from SVN and write to a header file:

Tuesday, October 08, 2019

Why I prefer exceptions to error codes

Why I prefer exceptions to error codes:
Error codes are far safer for well-reviewed, critical code ...for most code, failing early [with exceptions] is better simply because it always makes debugging easier – even if it doesn't make the impact of the error smaller... With an exception, you get a call stack, and an error string from the bottom layer.

Monday, October 07, 2019

FIFO queue use case

I have a simulation whose number of time steps varies according to inputs. To find the last state of the simulation via interpolation, I need to save the last N time steps. I can use a FIFO queue to save the results of last N time steps (e.g. to use in interpolation). Pseudocode:

step() {
    result = calcStateAtCurrentTime();
    queue.push(result);
    if(queue.size() > N) {
        queue.pop();
    }    
}

Bonus: To print unsigned int 64, use printf("%"PRId64", myUInt64)

Tuesday, October 01, 2019

Why you should take warning C4013 seriously

A piece of legacy C code that was working fine on Windows 7 64 bit was crashing on Windows 10 64 bit. After a couple of days of detective work I found out that it was related to warning C4013: 'malloc' undefined; assuming extern returning int. Simplified version of the code is as follows:
When I build the code with Visual Studio with the x64 platform selected, I get two warnings:

When I run it on a Windows 10 64 bit PC with x64 setting, I get access violation:

When I look at the variable m->a, I see "unable to read memory":

To solve the problem, I have to include stdlib.h:

Explanation: You get away with it on a 32 bit build because the size of int is the same as the size of a pointer. On the other hand if you build your program as 64 bit program, the warnings become really relevant, because now pointers are 64 bits wide, but as the compiler assumes that malloc etc. return ints (i.e. 32 bit instead of 64 bit for pointer) everything get messed up.

Why does the compiler issue a warning instead of an error, even tough it cannot find definition of malloc: The symbol foo, without a declaration, is totally unknown to the compiler. Because it just compiles your code, but it's not responsible for the linkage of your symbols (I say symbols because this can include variables and functions)... The linker sees the symbol foo(4 bytes) and will start to look for any corresponding definitions of foo(4 bytes). And if it finds that (say, in another module of yours, or in the libc of your system, or as syscall wrapper), then the linker is content and it will create the executable.

When I commented out the stdio.h include, I got C4013 warnings for both printf() and getchar() as expected, but I also got a linker error for printf: "LNK 2019 unresolved external symbol". When I looked inside stdio.h for their definitions, I saw that the definition of printf was more complex and contained __CRTDECL, defined in vcruntime.h which I think is part of visual studio specific libraries, not "core" C/C++. vcruntime.h resides under Program Files (x86)/Microsoft Visual Studio 14.0/VC/... folders, while stdio.h resides under Program Files (x86)/Windows Kits/10... folders. I guess the linker always looks into the standard libraries, even if you don't include their headers.

Why is it crashing on Windows7 64 bit but working fine on Windows 10 64 bit? I don't know :(

Bonus 1: You can configure Visual Studio to treat 4013 warning as error so that the build stops.

Bonus 2: All the different reasons that can lead to a LNK2019 unresolved external symbol error. Recently I got it because I tried to use a cpp function from a c file.

Music: Internal Conflict (Black Mesa: Xen Soundtrack) - Joel Nielsen

Friday, September 27, 2019

Real Time Operating Systems

A real time operating system (RTOS) guarantees that a user defined task will always take the same amount of time (determinism), there won't be surprise OS tasks interrupting and delaying the user task. The RTOS scheduler takes only task priorities into account, duration is the responsibility of the developer. If a task takes too long, you have two options: Simplify the task or use better hardware.

When dealing with low resource embedded systems, the OS should also be lightweight.

Using a kernel or OS ported to your target hardware liberates you from knowing the details of the hardware and writing device drivers.

Consider Windows: It might have higher priority tasks than yours which will cause your task to vary in duration at every run and it is not light weight. These are the reasons why Windows can't be used in low resource systems with real time constraints. See this StackOverflow post.

If you know basic kernel concepts like task scheduling, you don't need to know anything extra to understand an RTOS. For a good RTOS intro, see
  • Real Time Application Design Tutorial
    • Tasks will block until an event indicates that processing is required. Events can either be external (such as a key being pressed), or internal (such as a timer expiring). This event driven approach means that no CPU time is wasted polling for events that have not occurred. Priorities are allocated to tasks in accordance to their timing requirements. The stricter the timing requirement the higher the priority... The kernel will immediately suspend an executing task should a higher priority task become available... The kernel tick frequency should be set at the slowest value that provides the required time granularity.
  • Getting Started with Micrium OS.

Wednesday, September 18, 2019

Future Work

The following strike me as topics for research that would be realistic and could have enormous consequences:
  • Blockchain: Faster but still secure consensus mechanism to improve transaction bandwidth.
  • AI, object recognition: Statistical metric to assess quality of negative images to reduce time consuming trial and error. 

Tuesday, September 17, 2019

Why do we have different electoral systems?

Why do we sometimes have top down and other times bottom up elections? Examples:
  • Top down: During presidential elections people vote for the president and the parliament. After the election, the president appoints people to top jobs.
  • Bottom up: During worker's union elections workers vote for their representatives. The representatives vote for the union president (bottom up).
Do these election types have any logic depending on their context or are they a result of historical accidents?

Wednesday, August 28, 2019

Problem with mixing C++ and C code

In a C++ project that also contained legacy C files, I started to get the error "C2664 ...cannot convert argument 3 from void * to const_locale_t". The argument in question was NULL. Changing the include order by including the legacy header after stdio.h solved the problem but I wanted to understand the root problem to avaiod unnecessary technical debt.

One of the C headers contained #define NULL ((void *)0) which is standard for C but not for C++. Normally NULL is defined inside vcruntime.h (part of Visual C++). Using the legacy NULL before any code that depends on vcruntime.h, like string.h, stdio.h, caused this error. Removing the custom definition or changing it to the following solved the problem, see also my answer on StackOverflow:
Another strange error happens if you have defined fmax globally in your own C code because it also exists in cmath. The strange error will be C2039 'fmax': is not a member of 'global namespace'. Removing or renaming your own custom definition will solve the problem.

Monday, August 19, 2019

How to learn

Below are my learning steps with bitcoin/blockchain as an example:
  1. Heard the keyword bitcoin and got curious, read a few webpages, understood very little. Wondered what the use of mining was.
  2. Finally got the gist of it by watching But how does bitcoin actually work.
  3. To undertand blockchain in more detail, started implementing a simple version of blockchain (in progress)
  4. Review original paper, be able to follow research on the subject.
  5. Review original source code.
  6. Make improvements.
I use similar steps to learn AI. Last year I worked with an intern, this year a second intern is working on training openCV.

In general:
  1. Understand the general concept by watching short (~15min) videos.
  2. Know enough to define work for novices/interns.
  3. Be able to use existing tools.
  4. Be able to implement basic version.
  5. Follow literature.
  6. Make improvements.
This strategy makes sure that I always have something useful even when I do not reach the final step.

Thursday, August 01, 2019

Processing directory list in a Windows batch file

Handle a specific directory in current folder differently from other folders:
Note that if you only wanted to check if a directory existed, a simple EXIST would suffice.

Bonus: If you want to set the result of a command to a variable, you can use this. Note that you have to enclose the command with ` `, not ' '. This reminds me of my double quote problem in Visual Studio...

Wednesday, July 31, 2019

Treating failures as opportunities

Any non-trivial engineering project is bound to face failures / errors / bugs. Instead of haphazardly fixing the error, I propose the following approach:
  1. If you are in a hurry and there is a quick fix, fix it, but take note and do the following steps when you have more time.
  2. Analyze and repeat the problem, find the root cause and solve it.
  3. Improve error indicators (e.g. different blinking LED frequencies / beep sounds for different errors) and error messages. A good error message contains a description of the problem and possible work arounds, it there are any. You might think that you have solved the error for good but the same error might be triggered from a different path and then you will be glad that you have a nice error indicator helping you solve the problem in half an hour instead of a week.
  4. Add unit tests proving that the bug was solved and leaving a trail of what kinds of bugs had to be tackled with in the past.

Tuesday, July 30, 2019

Matlab: Dynamic cell array with string elements

In Matlab, to dynamically update cell array with string elements, use the following:

myCellArray = {}; %initializing cell array
for i=...
    myCellArray = [myCellArray; someString]; %dyn. update cell array
end

Note that when initializing the cell array you use curly brackets "{ }", while resizing the cell array you use square brackets "[ ]".

Monday, July 29, 2019

Software development maturity levels

Software development maturity levels are:
  1. Modular design and implementation.
  2. Nightly build script and pass/fail email.
  3. Automated tests with tools like Macro Scheduler.
  4. Unit tests.
  5. Continuous integration.
  6. Continuous deployment.

Friday, July 26, 2019

Asteroids game with JavaScript

Recently I watched the Make JavaScript Asteroids in less than one hour video and decided to give it a go. I changed the ship shape to make it clearer which side is the nose, added thrust animations and sound effects. Most of the sounds are my son's recordings. I did the thrust sounds with Audacity's pink and brown noises. My code is on GitHub. Game play in web browser video:

Wednesday, July 24, 2019

Transforming low-tech companies to high-tech

I have been involved in the digital transformation of low technology companies to high technology ones. The motivation for tranformation was competitive advantage, higher profit margins and diversification into new markets. 
Almost every organization seems to include digital transformation in its vision and strategy, but most struggle with executing digital transformation initiatives. There are myriad reasons: the challenges of introducing new technologies and providing the workforce with relevant skills, ensuring that the company’s culture and organizational structures are conducive to change, and anticipating correctly which processes need to change and how, to name a few.
Key areas that I had to oversee and lead were the following:
  1. Have short and to the point meetings, no excessive story telling.
  2. Focus on the right problems, i.e. good analysis, instead of wasting effort on poorly defined objectives.
  3. Create high tech transformation road map document.
  4. Instead of local server infrastructure, use cloud services (e.g. G Suite vs Office 365, GitHub) as much as possible. Prerequisite: Fast and reliable internet connection of all offices and factories.
  5. Mentor managers and lead engineers. Teach the importance and best practices of good documentation, reviews and good tests in achieving quality. Form a culture that embraces trial and error and treats failures as improvement opportunities. Focus on minimum viable products. Have short design/development/test cycles via sprints.
  6. Eliminate micromanagement, communicate business context.
  7. Develop critical tech (algorithms, software, electronics, tools, simulators/emulators and HWIL test infrastructure) in-house.
  8. Tailor certification standards to project scope because most standards are a mess.
  9. Make sure that quality procedures are adequate and applicable in real world scenarios.
  10. Improve hiring practives, form capable tech teams. Provide remote working opportunities to attract talent. Isolate them from mundane work to decrease turn-over rates.
  11. Improve information dissemination through wikis and forums. To improve technical docs, when an engineer is assigned to a task that he is a novice of, he also has to update documantation related to that task.
  12. Have methodologies in place to support remote work (daily scrum video conferences, sprints, Google Drive, GitHub etc.)
  13. Improve internet presence (dynamic web site, videos) for better marketing and recruitment.

Friday, July 19, 2019

Double quote problem in Visual Studio post-build event command line

Recently I was working with OpenCV and I had to copy a dll in Visual Studio 2017 post-build event. When I tried it I got "Error MSB3073 The command "copy ... exited with code 1". When I copied and pasted the command in the error message to cmd.exe, it worked! After one day of frustration, I realized that the double quote character in Visul Studio Post-Build Event Command Line was slightly different. I copied the non-working and working versions to Notepad++ and zoomed in. The first line has the wrong double quote and the second line has the correct one:
I wrote the line first in a Google Docs and then copy-pasted it to Visual Studio, which  preserved formatting for the double quote and gave me that strange error. It was not possible for me to spot the difference in Google Docs, I only noticed it when I zoomed in Notepad++. The unbearable lightness of software development...

Monday, July 15, 2019

Yemek yapmanın dayanılmaz ağırlığı

Günlük yemek yapmanın gerektirdiği zaman ve iş gücü can sıkıcı. Maddelersek:
  1. Her hafta en az bir kez pazara git.
  2. Her hafta en az bir kez markete git.
  3. Malzemeleri dolaplara yerleştir.
  4. Ekmek al.
  5. Hemen her gün ne yemek yapacağını düşün, yemek yapmak için malzemeleri yıka, doğra, pişir.
  6. Yemek malzeme kabukları ile dolan çöpü çıkar.
  7. Bulaşıkları makineye koy, yıkandıktan sonra geri çıkar.
  8. Yeterince yardımcı olmadığın için eşinden azar işit (!)
Rutin adımların dışında gerekenler:
  1. Bir sürü tencere, tava, tabak, çanak, kepçe, bıçak, kaşık.
  2. Çanak çömleği koymak için bir sürü dolap.
  3. Büyükçe bir lavabo ve bulaşıklık.
  4. Fırın.
  5. Mikrodalga.
  6. Ocak, tüp.
  7. Aspiratör.
  8. Bulaşık makinesi.
  9. Dondurucusu olan büyük bir buzdolabı.
  10. Mutfak robotu (rondo)
  11. Tüm bunlara ev sahipliği yapan mutfak.
Yemek yapmayın demiyorum, hobi olarak yine yapın (!) İnternetin ve lojistik imkanlarının gelişmesi sayesinde yemek abonelik sistemine geçmemek için teknik bir neden yok, geriye maliyet ve lezzet kalıyor. Yemek abonelik hizmetleri yeterince iyi ise mutfak ve içindekilere gerek olmayacak, evin bir köşesinde küçük bir buzdolabı ve mikrodalga yeterli olacaktır.

Hazır bu hafta kendi başıma evdeyken yemek servislerini deneyeyim dedim, MealBox ve Rafinera'yı inceledim ve Rafinera'yı seçtim. Sebebi MealBox şikayetlere cevap yazmazken Rafinera'nın cevap yazmasıydıRafinera'nın protein plus paketini beş gün denemeye karar verdim. Teslimat saati olarak üç seçenek var: 07:30-08:30, 08:30-09:30, 09:30-10:30. İlk sipariş yarın sabah geliyor, izlenimlerimi gün gün buraya yazacağım.

16.07.2019 (Gün 1/5): Sabah 08:25'te yemek kutum geldi (teslimat saati olarak 08:30-09:30 seçmiştim). Kahvaltı, öğle ve akşam yemekleri doyurucuydu. Demek ki 2100 kcal protein plus paketi benim gibi 80kg'lık biri için yeterli. Öğle ve akşam yemeklerini orjinal kaplarında, çatalla birkaç delik açarak mikrodalgada ısıttım, yanlarında biraz domates, maydanoz ve yoğurt yedim.

17.07.2019 (Gün 2/5): Bugün için teslimat saatini 07:30-08:30 seçtiğim halde saat 9'a kadar paket ulaşmayınca Rafinera'yı aradım. Paket 09:05'te elime ulaştı, teslim eden kurye polis çevirmesi nedeniyle yarım saat kaybettiğini söyledi. Biraz sonra Rafinera aradı ve bir önceki gün teslimat saatinin 08:30-09:30 olması nedeniyle karışıklık yaşandığını söyledi. Lojistik konusu iyileştirmeye açık görünüyor. Bugünkü menü:

Rafinera'yı ailecek (iki yetişkin, bir çocuk) yıl boyu kullanmak istesek durum nedir diye analiz ettim: Benim iş yerinde ve çocuğumun okulunda öğle yemeği çıkıyor, ancak eşimin iş yerinde öğle yemeği yok. Kahvaltı hazırlamak da kolay, kahvaltının gelmesine gerek yok. Bu nedenle hafta içi günde 1+1+2 = 4 dört yemeğe ihtiyacımız var. Hafta sonu yine kahvaltıyı kendimiz hazırlarız, günde 2+2+2 = 6 yemeğe ihtiyacımız var. Rafinera Pazar günleri çalışmıyor. Yani kabaca bir ayda 4*20 + 6*4 = 104 yemek gerekli. Rafinera resmi tatillerde de çalışmadığı için ortalama ayda 96 yemek diyelim. Kahvaltısız paket öğle akşam yemeği ile iki ara öğün içeriyor, yani hafta için her gün iki paket, C.tesi de üç paket işimizi görüyor. Şu anki fiyatlarla (klasik menü, kahvaltısız, 1900 kcal, 90+gün) aylık en az (4/2*20+6/2*4)*59*96/104 = 2832TL ediyor. Eğer üçümüz için ayrı ayrı tek öğünlük gündüz programını seçseydik 96*54=5184TL olurdu. Mesaimize yetişebilmemiz için teslimatın en geç 08:00'da yapılmasını da garantilersek bu iş olur. Teslimat saatiyle ilgili müşteri hizmetlerine mail attım, iki saat sonra Abdullah Bey aradı, lojistik sorumluları ile görüştüğünü, bizim adres için 08:15'i garantileyebileceklerini söyledi. Teşekkür ettim ve sabah en geç 8'i sağladıkları gün hazır müşterileri olduğumu söyledim.

Bize yakın Med Yemek şirketini arayıp aile paketleri var mı diye sordum, yemek servisleri olduğunu, bizim bulunduğumuz yere servisleri var mı diye bakıp döneceğini söyledi. Aradan yarım gün geçti, ses seda yok...

Diğer seçenekler: Diyetta, FormenaBaşak Ev Yemekleri, G4

18.07.2019 (Gün 3/5): Kutu sabah 07:25'te geldi.

19.07.2019 (Gün 4/5): Kutu sabah 07:50'de geldi.

20.07.2019 (Gün 5/5): Kutu sabah 08:15'te geldi.


Günün müziği:

Friday, May 31, 2019

NodeJS HTTP Server Timeout

In Nodejs an HTTP server created by http.createServer() has a default timout of 2 minutes (12000ms). I have an HTML client that calls the server through a GET request and the server starts a batch file that takes more than 5 minutes to finish. After two minutes, the server hits the timout and does some sort of restart (I guess), calls the batch file again and this continues ad infinitum, none of the client GET requests getting a return!

Solution: server.setTimeout(0); //disables timeout

Build Visual C++ Project from Command Line

Previously I showed how to build a couple of files from command line. To build a whole Visual C++ project from command line, I tried msbuild. However, I had no luck with it because I got "error TRK0002: Failed to execute command...". Then I used devenv and it worked perfectly. The following batch script did the job from a normal command line:

@DevEnvDir="c:\Program Files (x86)\Microsoft Visual Studio 14.0\Common7\IDE\"
@set PATH=%DevEnvDir%;%PATH%
@cd c:\temp\DeleteMe
@call devenv DeleteMe.sln /build "Release|x86"

Saturday, May 25, 2019

The secret to happiness

I have finally discovered the secret to happiness and I would like to share it with you [drumroll...]: It is doing the simple things every day! That doesn't sound very inspiring, does it? People expect some heroics that they have to do only a few times and then become fit, successful, effective, i.e. most of the prerequisites for a happy life. And they like explanations like genius and luck because it absolves them of guilt. Examples of simple things resulting in huge benefits in the long run:
If you are among the 90% who say that they don't have time, my answer is that your priorities are not right. What could possibly be better than investing in your health and child? Watching movies?

I once had a conversation with an uncle, about 65 years old. He said that he would give everything he had to be 20 years younger. He was in good health for his age. I asked him "uncle, 20 years from now, you will say the same thing again. Do you live your life in a way that someone would give his everything for?" My uncle kept silent...

Interestingly, when you tell others about learning how to fish, instead of having been handed a fish, they all nod in agreement. In reality, they want the fish! Recently I was chatting with my aunt, whose daughter plans to study abroad. I was giving advice about what to do. My aunt got impatient and said "Şamil, don't tell us what to do, do it for us". I became indignant and replied "if it was possible, you would be happy if I entered the university exam in her place, wouldn't you?!" She sheepishly said yes.

Seeing how difficult this simple action is for most, I became more motivated to instill perseverance in my child. And as you know, the only way to teach a child anything is to do it yourself and be an example first.

Saturday, May 11, 2019

Dünya'nın en güzel şarkısı

Deniz Tekin'in yorumuyla "Sezenler olmuş" şarkısını Dünya'nın en güzel şarkısı, güftesini de Dünya'nın en güzel şiiri ilan ediyorum. Şiirin birinci ve ikinci kısmındaki simetriye dikkat: Birinci kısımda "sen bendesin", ikinci kısımda "ben sendeyim"...



Bunu seven şunu da sevdi: Seni Kendime Sakladım - Duman (Oğulcan Başarı & Evrencan Gündüz)

Matlab: Save workspace to text file

In Matlab you can easily save workspace to a mat file. If you want to write workspace variables to a text file:

Friday, May 10, 2019

Letters to a novice programmer

Novice programmers create a lot of garbage code. Recently I refactored the code of a novice and reduced it by more than 10 times (360KB --> 30KB)! The most important rule for a novice would be to express the solution to a problem in as little code as possible. He should always ask himself "do I really need to write this line of code, can I combine those repeating sections to make it a function". All that code has to be debugged, reviewed, tested and maintained by yours truly.

Dear novice, treat code as something smelly and ugly, which is especially true for the code you produce and try to minimize it, remember how perfection is achieved. It is not your fault. If you follow my advice, you will soon become much better.

Thursday, May 09, 2019

Visual C++ DLL

When coding a C++ project that uses an existing dll, you also need to have the lib file to be able to build your project. Once you have built your project and created your exe, you only need the dll, not the lib.

Bonus: stringstream is slow, char* is faster.

Friday, May 03, 2019

The most important characteristics of an entrepreneur

I have worked with different types of entrepreneurs over the years and came to the conclusion that the most important characteristics of an entrepreneur is to have high energy and low pride. By low pride I mean not being offended easily. Average intelligence is enough until you want to exceed the 100M$ mark. In terms of monetary value:
  • High Energy + Low pride = 100M$
  • Medium Energy + Medium pride = 10M$
  • Low Energy + Low pride = You shouldn't be an entrepreneur
  • High Energy + High pride = You shouldn't be an entrepreneur
  • High Energy + Low pride + High intelligence = No upper limit to the wealth you can create

Friday, April 19, 2019

Accessing workspace from C-Mex s-function

In Matlab Simulink you can access workspace variables from a C-Mex (C++/C) s-function as follows:



To write to workspace from C-Mex, you can use
#include "matrix.h"
...
mxArray* pa = mxCreateDoubleScalar(12.34);
mexPutVariable("base", "myVarName", pa);

Note that you cannot use myVarName in a simulink block unless you call it before or during InitFcn.

Thursday, April 18, 2019

Matlab Simulink s-function handling of matrix (2D) type parameters

To demonstrate Matlab Simulink s-function handling of matrix (2D) type parameters, I prepared the following demo. The input is a constant block with "Interpret vector parameters as 1-D" unchecked and value [11, 12; 21, 22; 31, 32]:


Wednesday, April 10, 2019

Windows: Build C++ from command line

If you have Visual Studio 2017, to build a C++ project from a "normal" - not developer - command line:
  1. Add the following to system path: 
    1. To use cl.exe: c:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Tools\MSVC\14.12.25827\bin\Hostx64\x64\
    2. To use vcvars64.bat: c:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\
  2.  Open a command window and issue the following commands
    1. vcvars64
    2. If you are in a drive other than C:, let's say D:, you have to issue the command D: because after vcvars64, the drive reverts to C:
    3. cl a.cpp b.cpp
For example, in order to build mms-cpp, I created a batch with the following content:

set PATH=%PATH%;C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Tools\MSVC\14.12.25827\bin\Hostx64\x64\;C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\
call vcvars64
d:
call cl API.cpp Main.cpp

Note that there should be no whitespace after "PATH=" and the additional two paths should not be enclosed with quotation marks.

Sunday, April 07, 2019

Converting RC toy to bluetooth control

As a hobby electronics project, I converted the RC Mighty Excavator toy of my son to bluetooth control. I got rid of the original controller and we can now control the four DC motors of the toy from any Android phone or tablet.


This project had the following benefits:
  1. Learning how to control DC motors with motor drivers and PWM.
  2. Basic understanding of how to use a bluetooth module (HC-06)
  3. Soldering on a perfboard.
  4. Designing a basic PCB, getting it manufactored in China. The fact that EasyEDA works in the browser without the need to install anything, it's integration to JLCPCB and the low price and high quality of PCB production is fantastic.
Parts list:
  1. HC-06 Bluetooth module
  2. Arduino Pro Micro
  3. L293D driver (2x)
  4. PCB or perfboard
  5. 9V battery (2x)
  6. Arduino Bluetooth Controller app installed on Tablet.
Arduino source code is on gist.

End result:


Photos of the process:

Prototyping with Arduino Uno:


Perfboard top (Arduino Pro Micro and two L293 drivers):


Perfboard bottom (a soldering nightmare):


PCB that replaced perfboard:


Components placed on PCB:


Bluetooth module vertically squeezed between L293D and Arduino Pro Micro and soldered to Pro Micro:


PCB and batteries mounted to bottom of toy:


Tuesday, April 02, 2019

Eğitimin hal-i pür melali

Hafta sonu meşhur bir özel okulun ilkokul ikinci sınıfına giden yeğenimin matematik ödevini gördüm. Yeğenim 10 sorudan sadece birini doğru cevaplayabilmiş. Tanımadığım bir çocuk için 10 üzerinden 1 almış dense çocuğun matematikle pek alakasının olmadığını düşünürdüm. Kağıda bakınca yeğenimin çarpma ve toplama işlemlerini doğru yaptığını, işlem sırasını karıştırdığını gördüm, örneğin önce çarpıp toplayacağına toplayıp çarpmış. Doğru yaptığı 6. soru tek işlemden oluşuyor. Bu tür sorular Khan Academy'de 3.sınıf konusu ve 2-step word problems diye geçiyor.

Kardeşim okula teşhis ve tedavi için danıştığında "okuduğunu anlamıyor" cevabı almış, oysa kitap okumayı seven bir çocuktan bahsediyoruz. Doğru ifade "birden fazla aşama içeren problemlere hazır değil, daha basit problemlerle alıştırma yapması lazım" olmalı. Mevcut okul sistemi ustalaştıkça (mastery based) ilerlemeye değil, belli zaman periyotlarında belli konuların anlatılıp geçilmesine dayalı olduğundan eğer veli çocuğun eksiklerini evde gidermezse geride kalan çocuklar matematik fobisi geliştirip kendilerini tamamen kapatıyorlar, matematik katlanmak zorunda oldukları saçma bir eziyete dönüşüyor.

Okullardan ve eğitim sisteminden şikayet etmek pek bir işe yaramıyor, özel okullar da aynı sistemi uyguluyor. Çocuk senin çocuğun, ilgilenmek sana düşüyor. Eğitim sisteminin ustalık tabanlı yönteme geçmesine daha 100 yıl (!) olduğuna göre önerim Khan Academy ve Duolingo gibi online araçlarla çocukların veli gözetiminde desteklenmesidir.

Güncelleme 14.07.2019: Bu yazıdakileri anlattığım videoyu YouTube'a yükledim:

Team lead vs mentor

The difference between a team leader and mentor is that the team lead is responsible for meeting project deadlines while the mentor is concerned with personal development of mentees.

Thursday, March 21, 2019

Performance evaluation

Success of complex projects depends more on effective teams than rockstar programmers. Therefore, performance evaluation should focus more on the team than the individual. An individual's ability to make his teammates better is the highest achievement, his individual contribution is less important. If he does not fit into the team, he should leave. This implies that team members of similar rank should have similar pay. Pay and raise criteria should be made public. This results in less gossip.

Tuesday, March 05, 2019

Teaching English and mathematics to a six year old

My six year old son has learnt reading and writing which opened up a lot of opportunities. While thinking about how I could be more useful to him, I decided to try Duolingo for English teaching and Khan Academy for mathematics. Everyday at 18:30, I sit down with him and he first does Duolingo for 15 minutes, and then Khan Academy for another 15 minutes, for a total of half an hour a day. My role is to make sure that he really does the exercises and not play games or watch YouTube. I only help him when he gets stuck and requests my assistance.

Since both Duolingo and Khan Academy have curriculums that progress according to his level, I don't have to think about what to teach when. Khan Academy videos show me how to explain mathematical concepts to a child. Duolingo, besides training his English, also improves his reading and comprehension skills. Using the English version of Khan Academy also supports the language effort (of course, I have to translate math questions that have too many words in them to Turkish). The exercises show him the importance of paying attention to detail before jumping to conclusions, i.e. conscientiousness. Doing something every day is helpful in forming the most useful habit in life: persistence. And finally, he got rid of fearing failure and started to treat failure as a learning opportunity.

Friday, March 01, 2019

Scrum sprints

I propose the following sprints for software development:.
  1. Implementation sprint (4 weeks): Bugs are fixed, features are implemented. Output is software ready for informal testing, i.e. it can at least be built on the test computer and does not crash immediately when run.
  2. Design review & cleanup sprint (1 week): Review the highest priority and most problematic sections of software. Code is refactored according to design review results and clean code principles. Output is documentation of reviewed sections and cleaner code.
  3. Test sprint (1 week): Team decides on test scope, i.e. definition of "Done". As a minimum software should be built successfully on a clean hardware. Whole team tests the software. These tests are informal and limited to the Done definition. Tests should demonstrate that software is capable of passing the most important/frequent use cases, i.e. software is still in a useable state. Developers only fix bugs during this sprint, no design update is allowed. Output is a tag/snapshot. When you have automated tests with good coverage, you might not need a manual test sprint, because your software will be automatically tested at least once a day.
After these sprints, do a post mortem (1 day) to assess the efficiency of design, implementation and test sprints. Repeat this process until software is at a user acceptable quality level.

Friday, February 15, 2019

Technical reviews and mentoring

Recently a novice engineer sent a technical document for review, for which I was one of the reviewers. When I opened the document, I saw that it was littered with problems typical of a novice: No proper introduction explaining why this document was created, not specifying assumptions, simplifications and constraints, endless rows of data instead of clear graphs (i.e. signal buried in lots of noise), no clear conclusion, missing references, what still needs to be done, i.e. future work. See Why I gave your paper a Strong Reject

I told him that I will not review it and forwarded the document to a less senior colleague. As a grizzled veteran, I find it untolerably boring to provide basic feedback because I have done it a thousand times before.

How can we make both the novice and the veteran happy:

Monday, February 11, 2019

Remote working

Working from home (remote working) is used by many tech companies, e.g. Scott Hanselman from Microsoft. The main counter argument is that people will be less productive. It assumes that being physically present in an office for 8 hours makes you automatically more productive. My argument is that we have to measure productivity by examining the outputs, not by how much time has been spent. Also, design work requires high quality people and those types of people have less problems working on their own.

Risks and Mitigation
  • Not being able to use lab equipment:
    • Pure algorithm/software development requires no extra equipment other than a computer and internet connection. Examples of algorithm development: Guidance and control, navigation.
    • Most analyses are done on a PC with special software, e.g. finite element analysis, aerodynamic analysis.
    • Most equipment is relatively cheap and can be used at home (e.g. medium grade power supplies, oscilloscopes). For the remaining 10% of testing and analysis needs, you go to the lab. Criteria: If the equipment fits on your computer desk, it can be used at home.
  • Social isolation, loss of motivation
    • Assuming a four level hierarchy (team member -->  lead --> coordinator --> boss), organize daily online scrum meetings with tools like WhatsApp / Skype. Team leads meet with team members, coordinators meet with team leads and the boss meets with coordinators.
    • Issue tracking and sprint boards with Jira. Work in pairs with Teamviewer. Document sharing with Google Drive. Code repo with GitHub.
    • Weekly physical meetings at a central office or cafe.
    • Social events: Workshops at a resort, gym memberships, picnics, trekking, camping etc.
  • Distraction by kids, computer games, movies etc.
    • Have a saparete work computer that has no games on it.
    • Work at a quite place like a library and use your smartphone as a modem.
  • Not being able to measure productivity
    • As I already said above, this risk exists in physical offices too. The team lead is very important because the lead has to check and evaluate outputs (code, documents etc.) of team members and give them feedback on a daily basis. For persistent reporting, team members enter their daily progress as comments on the issue tracking system (e.g. Jira) which the lead will read. The same method will be used by coordinators to measure productivity of team leads. I assume that the coordinator is also technically adept and peeks into outputs and issue comments. Finally, how will the boss know that the teams are productive and not a waste of resources, especially if he does not have a technical background? This problem is not specific to working from home, so I will not go into further detail here.
  • Leak of confidential information
    • Most (>90%) technical work is not confidential, it is re-using public knowledge. Use designs/architectures suitable for isolating security related parts. Examples: 
      • Capture confidential information in data, not code.
      • Use emulators/simulators to test interfaces with dummy implementations. Most of the logic problems can be detected and resolved with dummy implementations. Test confidential implementations on site.
Advantages:
  • Attractive to talent --> You can select from a better talent pool.
  • Adapt work hours and environment to your personal preferences, reduce interrupts, resulting in better concentration (being in the zone) which increases efficiency by an order of magnitude.
  • Reduction of time wasted in traffic (in my case, 2 hours per day, i.e. 25% of the 8 hour work day).
  • Much better for families with little kids where daycare or dropping kids to school and picking up them up from school becomes a major issue.
  • Drastic reduction of logistics costs:
    • Less transport and related liabilities like traffic accidents.
    • Less office space --> Less building, heating, cleaning, maintaining.
    • Less cafeteria space, less cooking.
    • Fewer lavatory facilities and maintenance.
  • Reduction of city traffic and pollution.

Tuesday, January 29, 2019

How to outsource

The major benefit of outsourcing is to do more with less personel, to be shielded from human resources management issues and concentrate on the product. However, outsourcing work that is not clearly defined (like most research & development work) can be a headache if done haphazardly. By its very nature, most R&D work fails and should be treated as learning experiences. How can you outsource something that will most probably fail? I suggest dividing the task into the following three phases:
  1. Analysis: Concept of Operations, detailed requirements and acceptance test plans are generated.
  2. Design: Design documents and a minimum viable product that implements basic functionality is produced.
  3. Production: The end product covering all requirements is tested according to the acceptance test plan.
Instead of a single contract encompassing all three phases, each phase has its own contract. At the end of each phase, in order to continue to the next phase, both the contractor and the customer have to say GO. After that, the contract for the next phase is signed. The contractor gets paid only for the phase it has finished.

Note that for phases 1 and 2, there are no acceptance criteria for the deliverables, because adding additional criteria will drive the cost up. The contractor could submit a one page document and call it "requirements". The only leverage the customer has during these phases is the threat of not awarding the next phase and blacklisting. Therefore, most of the payment should be done in phase 3. If the total cost of the project is 100%, phase 1 should be 10%, phase 2 should be 20% and phase 3 should be 70%. Due to the relatively low cost, phases 1 and 2 could be awarded to multiple contractors to have some kind of competition.

Dividing the work into three phases protects the customer from mediocre contractors. At the end of phase 1 or phase 2, if the customer is not satisfied, armed with lessons learned and documents / prototype at hand, it can select another contractor. This phase structure also protects the contractor from fuzzy requirements and challenges that turn out to be technically impossible.

Friday, January 18, 2019

Good Variable names

Good code requires minimal comments to understand it. One of the best ways to achieve clarity is to use good variable names. Examples of bad variable names:
  • euler
  • h
  • azimuth
  • acc
Better variable names:
  • eulerRFB321NED2Body_rad: Rotated frame based Euler angles that will transform the NED frame to body fixed frame. Unit is radians. Note that array element order should be 0 = yaw, 1 = pitch, 2 = roll to reduce potential confusion.
  • hMSL_ft: Height above mean sea level. Unit is feet.
  • azimuthCWFromTrueNorth_deg: Azimuth measured clockwise from true North. Unit is degrees.
  • a_bi_NED_mps2: acceleration of body with respect to inertial frame, expressed in NED frame. Unit is m/s^2

Tuesday, January 15, 2019

Job attitude

Recently some novice engineers complained about their work, saying that it was boring. My own attitude towards my work is first and foremost "am I useful, do I add value". If I am not able to answer that question with a resounding yes, I have to find ways to make myself useful. Only after that do I allow myself to ask for more.

If you take initiative instead of complaining, you will go a long way, especially in fast growing environments, where there are many new challenges whose solutions nobody knows yet.

Similarly, if someone outside my workplace asks for my services, my first question is never "how much will you pay me" but "how can I be of help to you, is this problem worth solving".

As long as you keep on adding value, responsibility, respect and money will follow.

Sunday, January 13, 2019

Refactoring legacy embedded code

Recently we had to add new functionality to existing embedded software. When we analyzed the code, in many cases there were little to no documentation and code smells were all over the place. It was difficult to use existing functionality because it was very hard to understand. But replacing them with new clean code was not an option becaue the functions were used in many places. We would have to repeat costly HWIL and field tests, setting us back for months.

We decided to leave the existing functions but added comments about our suspicions, marked them as "deprecation candidate", wrote new ones that were only called from new code. We also heavily documented our additions. This approach is similar to changing public APIs: You rarely delete, you usually add and mark old code as deprecated so that existing software continues to function with the new API version.

To be able to update design/architecture, we first had to improve comprehensibility of existing code by removing clutter with these steps:
  1. Renamed variables, functions and classes to make them easier to understand.
  2. There were a lot of repeating code due to creation of new classes by copy-pasting old classes. We moved common code to utility classes/namespaces which made classes a lot lighter.
After performing the above two steps for a couple of months, we had a good grasp of what the code was trying to do. Think of it as discovering detailed requirements. Then we deleted dead code and out of date comments. Gradually we came up with simpler design ideas that would satisfy requirements.

Friday, January 11, 2019

Operational Amplifiers

Op-amps are used to amplify analog signals. By signal it is usually meant voltage, not current. So, op-amps amplify voltage. Their output current is low, on the order of mA.

In a control system, we usually want to drive a high current device like a motor or an electromagnet according to analog sensor (e.g. 49E) readings. Sensors output low voltage values which are amplified by an op-amp. In order to drive high current devices, we feed the op-amp output to a transistor that can handle higher currents. The reason we can't completely replace the op-amp with the transistor is that a transistor usually expects larger voltages at it's base (low current is not a problem) which the sensor cannot provide.

If your sensor output is not analog but digital (e.g. MPU6050 which has I2C output), you have to feed the output to a microcontroller which than can produce a PWM signal fed to the transistor, i.e. there is no op-amp in the digital sensor case.