Poslao: 30 Mar 2015 23:33
|
offline
- return void
- Anti Malware Fighter
Rank 1
- Pridružio: 02 Jan 2008
- Poruke: 2167
|
Ovo je kod koji sam napisao. Poenta je da se 6 brojeva (PIN) koje korisnik unese provere sa promenljivom koja vec ima neku vrednost (u ovom slucaju pin[7]). U koliko je uneti PIN isti kao i PIN koji je vec definisan u pin[7] promenljivoj, program treba da izbaci poruku da je pristup odobren. Ako nije isti PIN, da pristup nije odobren.
E sad, meni bez obzira na vrednost koju unesem izbacuje da pristup nije odobren. Zna li neko zasto je to tako?
I da, moze li se ovo resiti preko int tipa podataka recimo? Posto sam ja pokusao i to, ali kad stampam, uvek izbaci neke bez veze brojeve...
Btw, ovo je radjeno u visual studio ultimate 2010...
Evo koda:
// Pin kod.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include <string.h>
int _tmain(int argc, _TCHAR* argv[])
{
char pin[7]= "123456";
char provera[7];
int poredjenje;
printf ("Unesite Vas PIN:");
scanf_s ("%c", &provera);
poredjenje= strcmp (pin,provera);
if (poredjenje == 0)
{
printf ("Pristup odobren\n");
}
else
{
printf ("Pristup nije odobren\n");
}
return 0;
}
|
|
|
Registruj se da bi učestvovao u diskusiji. Registrovanim korisnicima se NE prikazuju reklame unutar poruka.
|
|
Poslao: 30 Mar 2015 23:43
|
offline
- vasa.93
- Moderator foruma
- Pridružio: 17 Dec 2007
- Poruke: 14822
- Gde živiš: Niš
|
Kao pojedinačnu konverziju u scanf_s koristi %s. %c je za karaktere, a %s za stringove. Zatim ti je operator referenciranja višak u toj naredbi, pošto promenljiva koju prenosiš već jeste referenca. Takođe, naravno da je moguće odraditi isto i sa integer vrednostima.
|
|
|
|
Poslao: 31 Mar 2015 00:05
|
offline
- return void
- Anti Malware Fighter
Rank 1
- Pridružio: 02 Jan 2008
- Poruke: 2167
|
Ispravio sam ovo za %s, ali sada se nista ne desava, vec samo mogu program da zatvorim.
Na koju promenljivu konkretno mislis?
Pa predpostavljam da moze i sa integer vrednostima, ali mi je problem sto pri stampanju, dobijam neke bez veze brojeve i zbog toga ne mogu da uporedim te dve vrednosti :/
|
|
|
|
Poslao: 31 Mar 2015 00:26
|
offline
- vasa.93
- Moderator foruma
- Pridružio: 17 Dec 2007
- Poruke: 14822
- Gde živiš: Niš
|
Napisano: 31 Mar 2015 0:25
Mislim na promenljivu provera. Ovako treba: scanf_s ("%s", provera);
Dopuna: 31 Mar 2015 0:26
Dalje, da proveriš kroz dibager gde je greška?
|
|
|
|
Poslao: 31 Mar 2015 01:16
|
offline
- return void
- Anti Malware Fighter
Rank 1
- Pridružio: 02 Jan 2008
- Poruke: 2167
|
Izmenio sam, ali onda program pukne i u debageru dobijam Run-Time Check Failure #2 - Stack around the variable 'provera' was corrupted. cim unesem vrednost.
|
|
|
|
Poslao: 01 Apr 2015 00:19
|
offline
- vasa.93
- Moderator foruma
- Pridružio: 17 Dec 2007
- Poruke: 14822
- Gde živiš: Niš
|
Napisano: 31 Mar 2015 7:37
Druže, kada radiš sa integer vrednostima, pin je jedan int, a drugi int unosiš i proveravaš da li su jednaki. Nema potrebe za više int promenljivih. Inače, nisam siguran što puca. Probaću danas da odradim pa javljam.
Dopuna: 01 Apr 2015 0:07
Tek sada primetih da radiš sa nekim generičkim VS projektom. _tmain funkcija ne postoji u "čistom" C++ jeziku. Evo rešenja koje radi: #include <stdio.h>
#include <string.h>
int main(int argc, char* argv[])
{
char pin[7] = "123456";
char provera[7];
int poredjenje;
printf("Unesite Vas PIN:");
scanf("%s", provera); //može i
//fgets(provera, 7, stdin); ili
//fscanf(stdin, "%s", provera); ili
//scanf_s("%s", provera, 7);
poredjenje = strcmp(pin, provera);
if (poredjenje == 0)
printf("Pristup odobren\n");
else
printf("Pristup nije odobren\n");
return 0;
} Kao što vidiš, glavna funkcija je main, a ne _tmain. _tmain je jedna od Microsoft-ovih ekstenzija. Generalno, ne bi bilo loše da uvek praviš prazan projekat (Empty project), a da onda u njemu kreiraš potrebne .c i .h fajlove o pišeš kod.
Dopuna: 01 Apr 2015 0:19
Dakle, scanf_s za razliku od scanf zahteva i veličinu bafera kao parametar. Naime, kod scanf_s nije moguć buffer overflow kao što je to slučaj kod scanf funkcije, pa je zbog toga veličine bafera neophodan parametar.
|
|
|
|
Poslao: 01 Apr 2015 15:44
|
offline
- bocke
- Moderator foruma
- Glavni moderator Linux foruma
- Pridružio: 16 Dec 2005
- Poruke: 12509
- Gde živiš: Južni pol
|
Kolio ja vidim, kod je čisti C. Ako je cilj bilo napisati C++ program onda bi bilo logičnije da se koriste input/output streamovi, a ne C IO funkcije.
Elem kad smo već kod scanf, ima svojih problema: scanf problemi. Ali scanf_s nije standardna ili portabilna funkcija, već MS ekstenzija. Ne postoji garancija da će raditi na drugim platformama ili čak na drugim verzijama Visual Studija. Potencijalno rešenje je prvo učitati liniju sa fgets, a zatim odraditi "formatiranje" sa sscanf.
|
|
|
|
Poslao: 01 Apr 2015 15:49
|
offline
- vasa.93
- Moderator foruma
- Pridružio: 17 Dec 2007
- Poruke: 14822
- Gde živiš: Niš
|
bocke ::Kolio ja vidim, kod je čisti C.Pa ono [C] u naslovu to i kaže.
|
|
|
|
Poslao: 01 Apr 2015 17:17
|
offline
- bocke
- Moderator foruma
- Glavni moderator Linux foruma
- Pridružio: 16 Dec 2005
- Poruke: 12509
- Gde živiš: Južni pol
|
Napisano: 01 Apr 2015 17:07
Sad vidim da je čovek napisao u naslovu C. Vaso, zbunjuješ.
Ali i on je napravio zabunu. C kod bi trebalo da se čuva u datotekama sa nastavkom c, a ne cpp. Razlog je i to što kompajler može neke stvari da posmatra drugačije u odnosu na jezik. Nisu C i C++ u potpunosti kompatibilni, iako su na nekom osnovnom nivou jako slični.
Dopuna: 01 Apr 2015 16:29
Evo moje verzije:
#include <stdio.h>
#include <string.h>
int main(int argc, char* argv[])
{
char pin[7] = "123456";
char provera[7];
int poredjenje;
printf("Unesite Vas PIN:");
fscanf(stdin, provera, "%s"); /* fscanf ima malo drugačiji raspored argumenata od scanf:
int fscanf(FILE *stream, const char *format, ....) */
poredjenje = strncmp(pin, provera, strlen(provera)); /* strcmp nije otporan na prelivanje bafera
zato ga menjamo sa strncmp koji ima jedan dodatni
argument:
int strncmp(const char *s1, const char *s2, size_t n) */
if (poredjenje == 0)
printf("Pristup odobren\n");
else
printf("Pristup nije odobren\n");
return 0;
}
Testirano sa mingw-w64 na Windows 7 64-bit.
Dopuna: 01 Apr 2015 16:56
Napravio sam grešku. Bilo mi je nešto sumnjivo pa sam hteo da proverim. fscanf je gotovo isto što i scanf. Preporučljivo je koristiti fgets i sscanf da bi se sprečilo prelivanje bafera. scanf i fscanf nisu preporučljivi, pogotovo ne kada je unos neočekivan.
Dopuna: 01 Apr 2015 16:58
Mislim, kod je validan, ali fscanf nije ništa sigurniji od scanf. Ne znam zašto sam to utripovao.
Dopuna: 01 Apr 2015 17:15
Pokušao sam još jednom, ali sam došao do verzije koja ne koristi nijednu od funkcija iz scanf familije. Ali proverava unos i trebala bi da je sigurnija.
#include <stdio.h>
#include <string.h>
int main(int argc, char* argv[])
{
char pin[7] = "123456";
char provera[7];
int poredjenje;
fputs("Unesite Vas PIN:", stdout);
fgets(provera, 7, stdin);
poredjenje = strncmp(pin, provera, strlen(provera));
if (poredjenje == 0)
puts("Pristup odobren");
else
puts("Pristup nije odobren");
return 0;
}
Problem je što takođe ne proverava ni format. Ali to ti nije ni potrebno pošto vršiš unos jedne string promenljive. Da ih ima više različitog formata, onda ovo ne bi radilo postao.
Toliko od mene. Odjavljujem se.
Dopuna: 01 Apr 2015 17:17
Još jedan dodatak. U ovoj mojoj varijanti ladno može i strcmp pošto smo već ograničili unos na 7 karaktera. Znači da su nam dužine oba stringa jednake.
E sad se odjavljujem.
|
|
|
|
|