test przetwarzania parametrów

0

Gnębi mnie ciekaowść i mam prośbę o wykonanie poniższego progamiku i wypisanie przy jakich opcjach kompilacji (o ile są) i przy jakim kompilatorze jakie otrzymaliście wyniki

#include <stdio.h>

void fun(int a,int b){
  if(a>b)printf("od prawej/ostatniego parametru\n");
  if(a==b)printf("wtf?!\n"); // nie powinno sie nigdy wykonac
  if(a<b)printf("od lewej/pierwszego parametru\n");
}

int main(){
  int i=1;
  fun(i++,i++);
  return 0;
}

gcc (GCC) 3.3.4 (pre 3.3.5 20040809)
-Os/-O2 i bez parametrów: od prawej/ostatniego parametru
-O3: od lewej/pierwszego parametru

gcc (GCC) 4.0.2 20050901 (prerelease) (SUSE Linux)
zabawa z -O* nic nie daje: od prawej/ostatniego parametru

Może ktoś wie również z czego to wynika ?

Prościutki teścik, kwestia kolejności operacji na parametrach funkcji, kolejności wrzucania parametrów na stos, czy jakolwiek to zwał.

0

Kwestia efektów ubocznych. Standardy C i C++ stwierdzają, że to zachowania nieokreślone. Po pierwsze kolejność ewaluacji argumentów jest nieokreślona, po drugie czas wystąpienia efektów ubocznych też - kompilator może to wedle fazy księżyca rozstawiać. Kompilator wybiera po prostu opcję, która wyda mu się najlepiej pasująca do danych warunków, jak oczekiwany sposób optymalizacji. Opcja 'wtf' jest możliwa - jeżeli efekty uboczne wystąpią po zwratościowaniu argumentów.

GCC 4.3.3 i LLVM 2.5 na Windows - 'od prawej/ostatniego parametru' w każdej możliwej konfiguracji.

0

Visual 2008 niezależnie od flag daje od prawej, chociaż raz zdarzyło się że skompilował do wtf. Ale to nie zmienia faktu, że nie masz tu makr ani wzorców, które mogłyby mieć parametry.

0
manfredek napisał(a)

Visual 2008 niezależnie od flag daje od prawej, chociaż raz zdarzyło się że skompilował do wtf.

Jeżeli robisz testy to rób je dokładnie, albo wcale. Wcześniej nie miałem Visuala pod ręką, teraz zapuściłem testy:

  • domyślna konfiguracja Debug - "od prawej/ostatniego parametru"
  • domyślna konfiguracja Release - "WTF"
    Opcje optymalizacji nie grają tu zbytniej roli, po porównaniu linii poleceń kompilatora widać charakterystyczną różnicę - parametry ustawiane w konfiguracji 'Basic Runtime Checks' (włączenie którejś wymaga wyłączenia optymalizacji):
  • /RTCs (tylko stos) /RTC1 (wszystkie testy) dają "od prawej/ostatniego parametru",
  • /RTCu (niezainicjalizowane zmienne) lub brak (domyślne) daje "WTF".

Przy włączonej optymalizacji wypisywanie WTF jest wbudowywane zamiast wywołania funkcji. Przy wyłączonej robi to co napisałem w poprzednim poście jako możliwe - efekty uboczne pojawiają się dopiero po wywołaniu funkcji. Dosyć osobliwe rozwiązanie. /RTC(s|1) zaś powoduje utworzenie kopii argumentów, wywołanie efektów ubocznych i przekazanie zachowanych argumentów.

Co do GCC i LLVM: na -Os dają to co Visual na optymalizacji - wbudowują putsa, bez optymalizacji inkrementacja, -O2\3 daje wbudowanie stałych.

Będę miał w tygodniu styczność z najnowszym Borlandem to się pobawię może i nim.

0

Digital Mars C++ (pod Windowsem, DOSa nie tykam) - niezależnie od ustawień - ciągnie od prawej.

1 użytkowników online, w tym zalogowanych: 0, gości: 1