diff --git a/arc b/arc
new file mode 100644
index 0000000000000000000000000000000000000000..3dfc5690e6dcd239daee5e47220b356c75ada1c7
--- /dev/null
+++ b/arc
@@ -0,0 +1,31 @@
+# Implementado por: Eduardo Machado e Victor Perszel
+# 2015
+
+CC=g++
+LIB=./lib
+INCLUDE=./include
+SRC=./src
+OBJ=./obj
+FLAGS = -w
+
+main:	connectionRawSocket messages miniShell submessages
+	$(CC) $(SRC)/main.cpp $(OBJ)/connectionRawSocket.o $(OBJ)/messages.o $(OBJ)/miniShell.o $(OBJ)/submessages.o $(FLAGS) -I$(INCLUDE) -L$(LIB) -o connection
+
+connectionRawSocket:
+	$(CC) -c $(SRC)/connectionRawSocket.cpp $(FLAGS) -I$(INCLUDE) -o $(OBJ)/connectionRawSocket.o
+	ar -cru $(LIB)/connectionRawSocket.a $(OBJ)/connectionRawSocket.o
+
+messages:
+	$(CC) -c $(SRC)/messages.cpp $(FLAGS) -I$(INCLUDE) -o $(OBJ)/messages.o
+	ar -cru $(LIB)/messages.a $(OBJ)/messages.o
+
+miniShell:
+	$(CC) -c $(SRC)/miniShell.cpp $(FLAGS) -I$(INCLUDE) -o $(OBJ)/miniShell.o
+	ar -cru $(LIB)/miniShell.a $(OBJ)/miniShell.o
+
+submessages:
+	$(CC) -c $(SRC)/submessages.cpp $(FLAGS) -I$(INCLUDE) -o $(OBJ)/submessages.o
+	ar -cru $(LIB)/submessages.a $(OBJ)/submessages.o
+
+clean:
+	rm connection $(SRC)/*~ $(OBJ)/*o $(LIB)/*a
diff --git a/connection b/connection
new file mode 100755
index 0000000000000000000000000000000000000000..1287e97f89a0545b1cef88caea32ab28384433c2
Binary files /dev/null and b/connection differ
diff --git a/john_maer.mp3 b/john_maer.mp3
new file mode 100644
index 0000000000000000000000000000000000000000..73b10d9b1d82e48c7a01480bfb0dbe253413d2bd
Binary files /dev/null and b/john_maer.mp3 differ
diff --git a/lib/connectionRawSocket.a b/lib/connectionRawSocket.a
new file mode 100644
index 0000000000000000000000000000000000000000..48d567a2dbae101c41430409b8169e41742fa170
Binary files /dev/null and b/lib/connectionRawSocket.a differ
diff --git a/lib/messages.a b/lib/messages.a
new file mode 100644
index 0000000000000000000000000000000000000000..8851c4e09ac209aeff350236aa6d33553150efe7
Binary files /dev/null and b/lib/messages.a differ
diff --git a/lib/miniShell.a b/lib/miniShell.a
new file mode 100644
index 0000000000000000000000000000000000000000..2748cf5263d5dab53f1a9fc7660d806d86c6978f
Binary files /dev/null and b/lib/miniShell.a differ
diff --git a/lib/submessages.a b/lib/submessages.a
new file mode 100644
index 0000000000000000000000000000000000000000..7026e9bbc890492e7b2246dbeda04ecda507a384
Binary files /dev/null and b/lib/submessages.a differ
diff --git a/obj/connectionRawSocket.o b/obj/connectionRawSocket.o
new file mode 100644
index 0000000000000000000000000000000000000000..ba1eba042c74e335d1d8674b6ee3dbc770a7b304
Binary files /dev/null and b/obj/connectionRawSocket.o differ
diff --git a/obj/messages.o b/obj/messages.o
new file mode 100644
index 0000000000000000000000000000000000000000..f1b7419a16636e5c5a5b0b0173631a2857fefd90
Binary files /dev/null and b/obj/messages.o differ
diff --git a/obj/miniShell.o b/obj/miniShell.o
new file mode 100644
index 0000000000000000000000000000000000000000..866fa9b2a66ff8c1c9fec7d733972bb6f8ccd882
Binary files /dev/null and b/obj/miniShell.o differ
diff --git a/obj/submessages.o b/obj/submessages.o
new file mode 100644
index 0000000000000000000000000000000000000000..d95dcfdde26bb3dd3ba69ac0a008b484ca86f2b4
Binary files /dev/null and b/obj/submessages.o differ
diff --git a/src/main.cpp b/src/main.cpp
index 9d1e6efe98331677dd334462172631d49e6eaeba..2fd8e022fc34737cf912576265058933d9a8e60b 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -61,6 +61,9 @@ int main(int argc, char *argv[]) {
       }else if(command == "put"){
         cin >> parameter;
         mainMessage.sendPUT((unsigned char*)(parameter.c_str()));
+      }else if(command == "get"){
+        cin >> parameter;
+        mainMessage.sendGET((unsigned char*)(parameter.c_str()), currentPath);
       }
     }
   }else if(service == "server"){
@@ -110,8 +113,20 @@ int main(int argc, char *argv[]) {
               send(soquete,resposta.objToString(),68, 0);
               if(mainMessage.receivePUT(serverReceive.getData(), currentPath) == 0){
                 cout << "arquivo recebido" << endl;
+              }else{
+                cout << "ERRO: put." << endl;
+              }
+            }
+          }else if(serverReceive.getType() == 6){
+            if(serverReceive.checkParity()){ // Se a paridade estiver errada
+              resposta.setData((unsigned char*)"6",0,0); // Manda um Nack
+              send(soquete,resposta.objToString(),68, 0);
+            } else {
+              if(mainMessage.receiveGET(serverReceive.getData()) == 0){
+                cout << "arquivo enviado" << endl;
+              }else{
+                cout << "ERRO: get." << endl;
               }
-              cout << "ERRO: put." << endl;
             }
           }
         }
diff --git a/src/messages.cpp b/src/messages.cpp
index 75f31cb559fb85a0700a51cfae22f450cb3dbe29..e18cd9449660dd34f159d6f83fb0c97144eb2076 100644
--- a/src/messages.cpp
+++ b/src/messages.cpp
@@ -137,9 +137,10 @@ int Message::sendLS(unsigned char* options){
 }
 
 int Message::sendPUT(unsigned char* fileName){
-  int error, success = 0, garbage, rv;
+  int error, success = 0, garbage, rv, length, i;
   char *receiptMessage = (char*)malloc(sizeof(char*)*68), fileSize[10];
-  string temp, fileData;
+  string temp;
+  unsigned char* fileData;
   struct pollfd ufds[1]; // usado para timeout em recv
   SubMessage put, answer, size;
   ifstream fileIn;
@@ -149,13 +150,27 @@ int Message::sendPUT(unsigned char* fileName){
 
   put.setData(fileName,5,0);
 
-  fileIn.open((char*)fileName, ios::in);
-  fileIn.seekg(0);
-cout << "PUT ===> 1" << endl;
-  while(getline(fileIn, temp)) {
-    fileData += temp + "\n";
+//   fileIn.open((char*)fileName, ios::in);
+//   fileIn.seekg(0);
+//   while(getline(fileIn, temp)) {
+//     fileData += temp + "\n";
+//   }
+  // Abertura do arquivo de entrada.
+  fileIn.open((char*)fileName, ios::binary);
+
+  // Contagem do tamanho do arquivo.
+  fileIn.seekg (0, ios::end);
+  length = fileIn.tellg();
+  fileIn.seekg (0, ios::beg);
+
+  // Alocação do vetor para a leitura do arquivo.
+  fileData = new unsigned char[length];
+
+  // Leitura.
+  for (i = 0; i < length; ++i){
+    fileIn.read((char*)&fileData[i], sizeof(unsigned char));
   }
-cout << "PUT ===> 2" << endl;
+
   while(!success){
     error = send(soquete, put.objToString(), 68, 0);
     if (error == -1){
@@ -171,22 +186,16 @@ cout << "PUT ===> 2" << endl;
           cout << "Erro no recebimento de resposta (messages.cpp::sendPUT)" << endl;
           return -1;
         } else {
-cout << "PUT ===> 3" << endl;
           recv(soquete, receiptMessage, 68, 0);
           answer.stringToObj((unsigned char*)receiptMessage);
-cout << "PUT ===> 4" << endl;
           // Lê começo da mensagem e vê se tem o delimitador de início
           if(answer.getStartMessage() == 0x7E){ // 0x7E = 01111110
             success = 1;
-cout << "PUT ===> 5" << endl;
             if(answer.getType() == 8){ // 8 = OK
               // OK, mandar tamanho
-              sprintf(fileSize, "%d", fileData.size());
-cout << "PUT ===> 6 (fileSize)" << fileSize << endl;
+              sprintf(fileSize, "%d", length);
               size.setData((unsigned char*)fileSize,9,0);
-cout << "PUT ===> 7" << endl;
               send(soquete, size.objToString(), 68, 0);
-cout << "PUT ===> 8" << endl;
               success = 0;
               while(!success){
                 rv = poll(ufds, 1, 500);
@@ -195,28 +204,22 @@ cout << "PUT ===> 8" << endl;
                     cout << "Erro no recebimento de resposta (messages.cpp::sendPUT)" << endl;
                     return -1;
                   } else {
-cout << "PUT ===> 9" << endl;
                     recv(soquete, receiptMessage, 68, 0);
-cout << "PUT ===> 10" << endl;
                     answer.stringToObj((unsigned char*)receiptMessage);
-cout << "PUT ===> 11" << endl;
                     if(answer.getStartMessage() == 0x7E){ // 0x7E = 01111110
                       if(answer.getType() == 8){
-cout << "PUT ===> 12" << endl;
                         success = 1;
-                        if(sendData((unsigned char*)fileData.c_str(), 13)){
+                        if(sendData(fileData, 13)){
                           cout << "Erro ao mandar dados (messages.cpp::sendPUT)" << endl;
                           return -1;
                         }
                       } else if (answer.getType() == 0){
-cout << "PUT ===> 13" << endl;
                         success = 0;
                       } else if (answer.getType() == 15){ // 15 = 0xE --> Erro
                         if(answer.getData()[0] == '2'){
                           cout << "Não tem espaço para mandar o arquivo" << endl;
                           return -1;
                         } else {
-cout << "PUT ===> 14" << endl;
                           success = 0;
                         }
                       }
@@ -225,7 +228,6 @@ cout << "PUT ===> 14" << endl;
                 }
               }
             } else if(answer.getType() == 0){ // 0 = NACK
-cout << "PUT ===> 15" << endl;
               // NACK
               success = 0; // reenvia pedido
             }
@@ -243,17 +245,27 @@ cout << "PUT ===> 15" << endl;
 int Message::sendGET(unsigned char* fileName, char* currentPath){
   int error, success = 0, garbage, rv, size, availableSize;
   char *receiptMessage = (char*)malloc(sizeof(char*)*68);
-  string temp, fileData;
+  string temp, fileData, arqName, receiveFile;
   struct pollfd ufds[1]; // usado para timeout em recv
   SubMessage get, answer, ack, nack, err, ok;
-  ofstream fileOut;
   struct statvfs *buff;
+  FILE* fileOut;
+
+  arqName += currentPath;
+  arqName += "/";
+  arqName += (char*)fileName;
+
+  fileOut = fopen(arqName.c_str(), "w");
+  if (fileOut == NULL){
+    cout << "Erro ao criar arquivo, saindo" << endl;
+    return -1;
+  }
 
   // Calcula espaço livre
   if(statvfs(currentPath, buff) == -1){
     cout << "Erro ao calcular espaço livre (messages.cpp::receivePUT)" << endl;
   }
-  availableSize = buff->f_bsize * buff->f_bfree;
+  availableSize = buff->f_bsize + buff->f_bfree;
 
   ufds[0].fd = soquete;
   ufds[0].events = POLLIN;
@@ -261,7 +273,7 @@ int Message::sendGET(unsigned char* fileName, char* currentPath){
   get.setData(fileName,6,0);
 
   while(!success){
-    error = send(soquete, get.objToString(), get.getSize()+4, 0);
+    error = send(soquete, get.objToString(), 68, 0);
     if (error == -1){
       cout << "Erro ao receber arquivo (messages.cpp::sendGET)" << endl;
     }
@@ -284,13 +296,13 @@ int Message::sendGET(unsigned char* fileName, char* currentPath){
             } else if (answer.getType() == 15){ // Erro
               if(answer.getData()[0] == '0'){
                 cout << "Arquivo Inexistente" << endl;
-                ack.setData((unsigned char*)answer.getSeq(),1,0);
+                ack.setData((unsigned char*)"0",1,0);
                 send(soquete, ack.objToString(), ack.getSize()+4, 0); // Manda um ACK
                 return -1;
               } else if (answer.getData()[0] == '1'){
                 cout << "Sem permissão para baixar o arquivo" << endl;
-                ack.setData((unsigned char*)answer.getSeq(),1,0);
-                send(soquete, ack.objToString(), ack.getSize()+4, 0); // Manda um ACK
+                ack.setData((unsigned char*)"0",1,0);
+                send(soquete, ack.objToString(), 68, 0); // Manda um ACK
                 return -1;
               } else {
                 success = 0;
@@ -298,20 +310,24 @@ int Message::sendGET(unsigned char* fileName, char* currentPath){
             } else if (answer.getType() == 9){ // Tamanho
               size = atoi((char*)answer.getData());
               if(availableSize < size){
-                err.setData((unsigned char*)answer.getSeq(),1,0);
-                send(soquete, err.objToString(), err.getSize()+4, 0); // Erro
+                cout << "Sem espaço." << endl;
+                err.setData((unsigned char*)"0",1,0);
+                send(soquete, err.objToString(), 68, 0); // Erro
                 return -1;
               } else if(answer.checkParity()){
-                nack.setData((unsigned char*)answer.getSeq(),0,0); // Manda um nack
-                send(soquete,nack.objToString(),nack.getSize()+4, 0);
+                nack.setData((unsigned char*)"0",0,0); // Manda um nack
+                send(soquete,nack.objToString(),68, 0);
                 return -1;
               } else {
-                ok.setData((unsigned char*)answer.getSeq(),8,0); // Manda um ok
-                send(soquete,ok.objToString(),ok.getSize()+4, 0);
-                if(receiveData(13) == ""){
+                ok.setData((unsigned char*)"0",8,0); // Manda um ok
+                send(soquete,ok.objToString(),68, 0);
+                receiveFile = receiveData(13);
+                if(receiveFile == ""){
                   cout << "Erro no recebimento de dados (messages.cpp::sendGET)" << endl;
                   return -1;
                 } else {
+                  fputs(receiveFile.c_str(),fileOut);
+                  fclose(fileOut);
                   cout << "Arquivo transferido com sucesso" << endl;
                   return 0;
                 }
@@ -531,11 +547,11 @@ int Message::receiveGET(unsigned char* fileName){
   ufds[0].events = POLLIN;
 
   if(access((char*)fileName, F_OK) == -1){ // Verifica se o arquivo existe
-    resposta.setData((unsigned char*)'0',14,0); // Manda um Erro
-    send(soquete,resposta.objToString(),resposta.getSize()+4, 0);
+    resposta.setData((unsigned char*)"0",14,0); // Manda um Erro
+    send(soquete,resposta.objToString(),68, 0);
   } else if (access((char*)fileName, R_OK) == -1){ // Verifica permissão de copiar o arquivo
-    resposta.setData((unsigned char*)'1',14,0); // Manda um Erro
-    send(soquete,resposta.objToString(),resposta.getSize()+4, 0);
+    resposta.setData((unsigned char*)"1",14,0); // Manda um Erro
+    send(soquete,resposta.objToString(),68, 0);
   } else {
     // Calcula o tamanho do arquivo
     file.seekg (0, ios::end);
@@ -600,9 +616,14 @@ int Message::receivePUT(unsigned char* fileName, char* currentPath){
   struct pollfd ufds[1];
   ufds[0].fd = soquete;
   ufds[0].events = POLLIN;
-  string receivedFile;
+  string receivedFile, arqName = "";
   FILE *fileOut;
-  fileOut = fopen((char*)fileName, "w");
+
+  arqName += currentPath;
+  arqName += "/";
+  arqName += (char*)fileName;
+
+  fileOut = fopen(arqName.c_str(), "w");
   if (fileOut == NULL){
     cout << "Erro ao criar arquivo, saindo" << endl;
     return -1;