Translate

Mostrar mensagens com a etiqueta Padawan. Mostrar todas as mensagens
Mostrar mensagens com a etiqueta Padawan. Mostrar todas as mensagens

sábado, 14 de dezembro de 2024

JSON em COBOL no IBM Z: O Holocron das APIs Modernas

 

Bellacosa Mainframe COBOL com JSON

JSON em COBOL no IBM Z: O Holocron das APIs Modernas

Como um Linguagem Criada em 1959 Aprendeu a Conversar com APIs, Mobile, Open Banking e a Nuvem

Por muitos anos, o universo COBOL parecia limitado a arquivos VSAM, DB2, IMS, CICS, JCLs e relatórios batch executados silenciosamente nos datacenters. Entretanto, a transformação digital trouxe novos desafios e uma nova linguagem passou a dominar a comunicação entre aplicações modernas: JSON (JavaScript Object Notation).

Hoje, smartphones, microsserviços, OpenShift, Open Banking, PIX, aplicações em nuvem e plataformas de inteligência artificial utilizam JSON como principal formato de intercâmbio de informações. E o mais interessante é que o Enterprise COBOL para IBM Z evoluiu para participar naturalmente desse ecossistema.

Com a introdução das instruções JSON PARSE e JSON GENERATE no Enterprise COBOL 6.x, programas COBOL passaram a compreender, produzir e consumir documentos JSON de forma nativa, eficiente e segura, permitindo a integração com APIs REST, IBM MQ, Kafka, z/OS Connect e arquiteturas modernas baseadas em eventos.

Esta série especial Bellacosa Mainframe apresenta uma jornada completa para o jovem Padawan COBOL compreender desde os conceitos básicos até técnicas avançadas utilizadas por especialistas IBM Z.


📖 Capítulo 1 – O Despertar do JSON

Quando o Padawan Descobre que COBOL Pode Falar a Linguagem das APIs

Neste primeiro holocron, exploramos os fundamentos do JSON, sua história, a chegada do suporte nativo ao Enterprise COBOL, diferenças entre JSON e XML, conceitos de UTF-8 e EBCDIC, além dos primeiros exemplos utilizando JSON GENERATE.

➡️ https://eljefemidnightlunch.blogspot.com/2024/07/json-em-cobol-no-ibm-z-o-holocron-das.html


📖 Capítulo 2 – JSON PARSE

Quando o Padawan Aprende a Transformar Texto em Estruturas COBOL

Aqui mergulhamos na instrução JSON PARSE, aprendendo a converter documentos JSON em estruturas COBOL, trabalhar com objetos aninhados, vetores utilizando OCCURS, tratar exceções, validar payloads recebidos e compreender os desafios relacionados à segurança e ao processamento de grandes volumes de dados.

➡️ https://eljefemidnightlunch.blogspot.com/2024/09/json-em-cobol-no-ibm-z-o-holocron-das.html


📖 Capítulo 3 – JSON GENERATE

Quando o Padawan Aprende a Construir APIs REST com COBOL

No terceiro capítulo, estudamos JSON GENERATE, recursos como SUPPRESS, NAME OF, tratamento de campos opcionais, construção de respostas para APIs REST, geração de payloads PIX e Open Banking, além de recomendações de desempenho e proteção contra exposição acidental de informações sensíveis.

➡️ https://eljefemidnightlunch.blogspot.com/2024/10/json-em-cobol-no-ibm-z-o-holocron-das.html


📖 Capítulo 4 – JSON Jedi Master

z/OS Connect, MQ, Kafka, OpenShift, OWASP e as Técnicas Jedi do IBM Z

No capítulo final, elevamos o nível de conhecimento para arquiteturas corporativas modernas. Exploramos o papel do z/OS Connect, integração com IBM MQ, Kafka, OpenShift, APIs de alto desempenho, conceitos da OWASP API Top 10, estratégias de observabilidade, segurança, escalabilidade e as melhores práticas adotadas por equipes especializadas em IBM Z.

➡️ https://eljefemidnightlunch.blogspot.com/2024/11/json-em-cobol-no-ibm-z-o-holocron-das.html


O Conselho Final do Mestre Bellacosa

Durante décadas, disseram aos desenvolvedores COBOL que sua missão terminava em arquivos sequenciais e terminais verdes. O JSON mostrou exatamente o contrário. Ele permitiu que programas escritos há décadas passassem a conversar com smartphones, microsserviços, aplicações em nuvem e plataformas digitais espalhadas por toda a galáxia tecnológica.

COBOL não precisou abandonar sua robustez, estabilidade ou capacidade de processar milhões de transações por segundo. Ele apenas aprendeu um novo idioma.

E talvez esta seja a maior lição deste Holocron:

COBOL não é uma tecnologia do passado.

COBOL é um veterano experiente que aprendeu a falar a língua do futuro.

Que o JSON PARSE esteja com você. E que o JSON GENERATE jamais exponha uma senha em produção. 🚀💙🖥️


Para ir mais longe

🔥☕ Como se Usa JSON em COBOL?

Nos últimos anos, o JSON (JavaScript Object Notation) tornou-se o formato mais utilizado para integração entre aplicações modernas, APIs REST, Mobile, Cloud e Mainframe.

https://eljefemidnightlunch.blogspot.com/2007/02/como-se-usa-json-em-cobol.html

🔥☕ JSON: O “COBOL DOS DADOS MODERNOS”? — A Linguagem Invisível Que Dominou APIs, Nuvem e Até o Mainframe

https://eljefemidnightlunch.blogspot.com/2010/10/json-o-cobol-dos-dados-modernos.html


sábado, 9 de novembro de 2024

JSON em COBOL no IBM Z: O Holocron das APIs Modernas – JSON Jedi Master - Parte IV

 

Bellacosa Mainframe e o json no cobol parte iv

JSON em COBOL no IBM Z: O Holocron das APIs Modernas

Parte 4 – JSON Jedi Master

z/OS Connect, MQ, Kafka, OpenShift, APIs de Alto Desempenho, Segurança OWASP e as Técnicas Jedi do IBM Z

Por Bellacosa Mainframe


"O Padawan aprende JSON PARSE. O Cavaleiro domina JSON GENERATE. O Mestre compreende que JSON é apenas a linguagem utilizada para conectar mundos inteiros."

Mestre Bellacosa Sysprog Jedi


Introdução

Chegamos ao último holocron.

Na Parte 1 aprendemos:

  • JSON

  • JSON GENERATE

  • UTF8

  • APIs

Na Parte 2:

  • JSON PARSE

  • Arrays

  • OCCURS

  • Segurança

Na Parte 3:

  • JSON GENERATE avançado

  • SUPPRESS

  • NAME OF

  • APIs REST

Agora chegamos ao nível do Mestre.

O momento em que COBOL deixa de apenas processar JSON.

E passa a ser um participante ativo de arquiteturas modernas.


O grande segredo

Muitos ainda imaginam.

COBOL

Batch

Relatório

Fim.

Mas o IBM Z moderno é muito diferente.

Hoje podemos encontrar:

COBOL

JSON

API

Mobile

Cloud

Kafka

OpenShift

IA

Aplicações Web


O papel do JSON

JSON tornou-se.

O idioma universal.


Imagine.

Banco.

Aplicativo.

PIX.

Open Finance.

Cartão.

Seguro.

Marketplace.

IoT.


Praticamente todos utilizam.

JSON.


z/OS Connect

Talvez seja a tecnologia mais importante.

Para o COBOL moderno.


O que é?

Uma ponte.

Entre.

IBM Z.

E.

REST APIs.


Visualmente.

Smartphone

↓

REST

↓

z/OS Connect

↓

COBOL

↓

DB2

Exemplo

Usuário.

Consulta saldo.

Aplicativo.

HTTPS

z/OS Connect

JSON

COBOL

DB2

JSON

Aplicativo


Tudo transparente.


COBOL não vê HTTP

Na maioria dos casos.

Não.


Ele apenas recebe.

Estrutura.

COBOL.

Já preenchida.


Exemplo.

01 WS-CONTA.


05 AGENCIA.


05 CONTA.



JSON PARSE.

Feito.

Automaticamente.


MQ

Outro caso.

Muito comum.


Mensagem.

Chega.

MQ.


Payload.

JSON.


COBOL.

Processa.


Exemplo.

{

"tipo":"pix",

"valor":100

}

COBOL.

Recebe.


Executa.

Negócio.


Responde.


JSON GENERATE.


MQPUT.


Fim.


Kafka

Sim.

Também.


Arquitetura.

COBOL

↓

MQ

↓

Kafka Bridge

↓

Kafka

↓

Analytics

Muito utilizado.


Open Finance.


Fraudes.


IA.


Big Data.


OpenShift

Outro mundo.

Interessante.


Microsserviços.

Containers.

Kubernetes.


COBOL.

Participa.


Arquitetura.

OpenShift

↓

REST

↓

zOS Connect

↓

COBOL

↓

IMS

DB2

Muito elegante.


APIs síncronas

Cliente.

Espera.

Resposta.


Exemplo.

Saldo.


API.

Responde.

200 ms.


APIs assíncronas

MQ.

Kafka.

Evento.


Mais modernas.


GraphQL

Também possível.


Embora.

Menos comum.


Segurança

Aqui começa.

O lado sombrio.


OWASP.

Existe.

Também.

Para APIs.


OWASP API Top 10

Excelente leitura.


Problemas.

Mais comuns.


Excesso.

Dados.


Exposição.

Sensível.


Autorização.

Fraca.


Payload.

Gigante.


DoS.


Exemplo ruim

COBOL.

01 CLIENTE.


05 CPF.


05 SENHA.


05 TOKEN.

JSON GENERATE.


API.


Exposta.


Desastre.


Melhor

Criar DTO.


Exemplo.

01 API-CLIENTE.


05 NOME.


05 LIMITE.

Muito melhor.


JWT

Muito utilizado.


JSON Web Token.


Aplicação.

Recebe.


Valida.


Autoriza.


COBOL.

Pode.

Consumir.


Ou.

Delegar.


TLS

Obrigatório.

Hoje.


HTTPS.

Sempre.


Nunca.

HTTP.


Rate Limit

Muito importante.


Evita.

DoS.


Exemplo.

Chamadas.

Por minuto.


Logs

Essenciais.


Exemplo.

2026-06-25


PIX


100 reais


OK

Muito útil.


Auditoria.


Performance

JSON.

Tem custo.


Parser.

CPU.


Serializer.

CPU.


Mas.

IBM Z.

É extremamente eficiente.


Benchmarks.

Mostram.

Milhares.

TPS.


Sem dificuldades.


JSON gigantesco

Cuidado.


Exemplo.

50 MB.


Parser.

Vai sofrer.


CPU.

Memória.


Melhor.

Paginar.


Streaming

Excelente opção.


Processar.

Em partes.


Mais eficiente.


Cache

Pode ajudar.


JSON.

Já montado.


Evita.

JSON GENERATE.

Toda vez.


Curiosidade

Muitos bancos.

Geram.

Milhões.

JSON.

Por hora.


E.

Grande parte.

Nasce.

Em COBOL.


Curiosidade 2

Usuário.

Abre.

App.


Consulta.

Saldo.


Recebe.

JSON.


Origem.

Programa COBOL.

Escrito.


Executando.

Num.

IBM z17.


Curiosidade 3

Muitos.

Open Banking.

Brasileiros.

Passam.

Por.

COBOL.

Sem.

Que.

Usuário.

Perceba.


Bellacosa Best Practices

Regra 1

Nunca.

Gerar.

JSON.

Com STRING.


Regra 2

JSON GENERATE.

Sempre.


Regra 3

JSON PARSE.

Sempre.


Regra 4

Versione.

APIs.


Exemplo.

v1

v2

v3


Regra 5

OpenAPI.

Swagger.

Documente.


Regra 6

Nunca.

Expor.

Campos internos.


Regra 7

Teste.

UTF8.


Regra 8

Monitore.

SMF.

RMF.

Logs.


Regra 9

Valide.

Payloads.


Regra 10

Use.

OWASP.

API Top 10.


Quando usar JSON?

Excelente.

REST.

Open Banking.

PIX.

Cloud.

Kafka.

MQ.

OpenShift.

Mobile.

Marketplace.

IoT.

Microsserviços.


Quando evitar?

Batch.

VSAM.

Arquivos internos.

Processamento.

Fechado.


O Conselho Final do Mestre Bellacosa

Durante muito tempo, disseram ao desenvolvedor COBOL que seu universo terminava em arquivos sequenciais, JCLs, relatórios impressos e terminais verdes.

JSON mostrou que isso nunca foi verdade.

JSON permitiu que programas escritos décadas atrás passassem a conversar com smartphones, aplicativos financeiros, plataformas Open Banking, clusters OpenShift, sistemas Kafka e serviços espalhados por diversas nuvens.

Talvez essa seja a maior beleza do IBM Z moderno.

Ele não obriga ninguém a abandonar o COBOL.

Ele apenas entrega novas ferramentas.

E diz:

Continue usando seus níveis 01, 05, 10 e OCCURS.

Continue confiando na robustez do Enterprise COBOL.

Continue processando milhões de transações por segundo.

Eu apenas ensinarei seu programa a falar o idioma utilizado pela galáxia digital.

E talvez essa seja a verdadeira lição do Holocron JSON.

JSON não substituiu COBOL.

JSON apenas permitiu que COBOL expandisse sua voz para além dos corredores do datacenter, alcançando praticamente qualquer sistema capaz de compreender uma simples mensagem cercada por chaves e aspas.


Fim do Holocron Bellacosa Mainframe

JSON em COBOL no IBM Z – Parte 1 a Parte 4 concluídas

"Que o JSON PARSE esteja com você. E que o JSON GENERATE nunca produza um campo SENHA por engano." 🚀💙🖥️


quinta-feira, 18 de julho de 2024

JSON em COBOL no IBM Z: O Holocron das APIs Modernas – O Despertar do JSON - Parte I

 

Bellacosa Mainframe e o json no cobol parte I

JSON em COBOL no IBM Z: O Holocron das APIs Modernas

Parte 1 – O Despertar do JSON

Quando o Padawan Descobre que COBOL Pode Falar a Linguagem das APIs

Por Bellacosa Mainframe


"Por décadas, COBOL falou VSAM, DB2, IMS e MQ. Hoje ele também conversa com APIs, microsserviços e nuvens distantes. O idioma escolhido pela galáxia moderna chama-se JSON."

Mestre Bellacosa Sysprog Jedi


Introdução

Durante muitos anos, a vida do desenvolvedor COBOL era relativamente previsível.

Ele acordava.

Abria o ISPF.

Editava um programa.

Fazia um READ em um VSAM.

Consultava um DB2.

Chamava um CICS.

Enviava uma mensagem MQ.

Executava o JOB.

Analisava o SDSF.

E ia tomar café.

Então, por volta da década de 2010, uma nova criatura começou a aparecer nas especificações técnicas.

Ela vinha acompanhada de nomes estranhos.

REST.

OpenAPI.

Swagger.

Microservices.

Kubernetes.

OpenShift.

APIs.

Mobile.

Cloud.

E no meio de tudo isso, um pequeno formato textual se tornou praticamente o idioma universal da integração moderna.

Seu nome era:

JSON

(JavaScript Object Notation)

E então o jovem Padawan COBOL perguntou:

Mestre...

Quer dizer que meu programa COBOL de 30 anos pode conversar com um aplicativo Android?

Pode responder uma API REST?

Pode enviar dados para um microsserviço em OpenShift?

Pode participar de uma arquitetura moderna?

O mestre sorri.

Olha para o IBM z17.

E responde:

Sim.

E o idioma utilizado para essa conversa provavelmente será JSON.


O que é JSON?

JSON significa:

JavaScript Object Notation.

Mas não se deixe enganar pelo nome.

Hoje JSON pertence ao mundo inteiro.

Não é apenas JavaScript.

É utilizado por:

  • COBOL

  • Java

  • Python

  • Go

  • Rust

  • Node.js

  • C#

  • Kotlin

  • Swift

  • APIs REST

  • OpenShift

  • Kafka

  • IBM MQ

  • z/OS Connect

Praticamente tudo.


Exemplo simples

Um cliente.

Em COBOL.

Temos:

01 WS-CLIENTE.

   05 WS-ID.

      PIC 9(5).

   05 WS-NOME.

      PIC X(30).

   05 WS-IDADE.

      PIC 999.

Em JSON.

{
  "id":100,
  "nome":"Bellacosa",
  "idade":52
}

Mesmo dado.

Representações diferentes.


Por que JSON venceu XML?

Muitos veteranos perguntam:

Mestre...

Mas XML não fazia isso antes?

Sim.

Fazia.

E ainda faz.

Mas JSON trouxe algumas vantagens.


XML

<cliente>

<id>100</id>

<nome>Bellacosa</nome>

</cliente>

JSON

{
"id":100,
"nome":"Bellacosa"
}

Menor.

Mais leve.

Mais rápido.

Mais amigável.


JSON chegou tarde ao COBOL?

Sim.

Durante muitos anos, programadores precisavam utilizar:

Parsers.

Ferramentas externas.

Java.

C.

SAX.

DOM.

Bibliotecas proprietárias.

Era desagradável.


Quando surgiu suporte nativo?

IBM introduziu suporte moderno em:

Enterprise COBOL V6

Especialmente.

COBOL 6.1

6.2

6.3

6.4

6.5


Duas instruções mudaram tudo.

JSON PARSE

JSON GENERATE

Essas duas instruções transformaram COBOL em um cidadão de primeira classe no universo das APIs.


O que é JSON PARSE?

É o tradutor.

Recebe texto.

Produz estruturas COBOL.


Visualmente.

JSON


↓

JSON PARSE


↓

WORKING STORAGE

O que é JSON GENERATE?

Faz o contrário.

WORKING STORAGE


↓

JSON GENERATE


↓

Texto JSON

Primeiro exemplo do Padawan

Passo 1

Criar estrutura.

01 WS-CLIENTE.

   05 WS-ID.

      PIC 9(5).

   05 WS-NOME.

      PIC X(30).

   05 WS-IDADE.

      PIC 999.

Passo 2

Criar buffer.

01 WS-JSON.

PIC X(200).

Passo 3

Popular dados.

MOVE 100

TO WS-ID


MOVE 'BELLACOSA'

TO WS-NOME


MOVE 52

TO WS-IDADE

Passo 4

Gerar JSON.

JSON GENERATE WS-JSON

FROM WS-CLIENTE

Passo 5

Display.

DISPLAY WS-JSON

Resultado.

{
"id":100,
"nome":"BELLACOSA",
"idade":52
}

Pronto.

COBOL falando JSON.


Como funciona internamente?

Aqui começa a magia.

O compilador gera código otimizado.

Percorre estrutura COBOL.

Mapeia campos.

Converte.

Monta texto.

Tudo automaticamente.


Visualmente.

WORKING STORAGE


↓

Field Scanner


↓

Serializer


↓

UTF-8


↓

JSON Buffer

Como JSON fica na memória?

JSON é texto.

Normalmente.

UTF-8.


Exemplo.

{"nome":"Bellacosa"}

Na memória.

7B

22

6E

6F

6D

65

Bytes.


CCSID

Muito importante.

Padawan frequentemente esquece.

IBM Z trabalha com:

EBCDIC.

JSON trabalha com:

UTF-8.


Complicação.


Exemplo.

COBOL.

EBCDIC

API.

UTF8

Conversão necessária.


Exemplo

Nome.

José


UTF8.

Dois bytes.


EBCDIC.

Outro código.


Pode quebrar.


Segurança

Muito importante.

JSON pode ser perigoso.


Exemplo.

Payload enorme.

{
"clientes":[

100000 itens

]
}

Pode consumir.

CPU.

Memória.

Tempo.


Boa prática.

Validar tamanho.


JSON Injection

Também existe.


Nunca confiar.

Em entrada.

Externa.


Sempre validar.


Arrays

JSON suporta.

{
"clientes":[

{"id":1},

{"id":2}

]
}

COBOL.

OCCURS.


Excelente integração.


Objetos aninhados

{
"cliente":{

"id":1,

"endereco":{

"cidade":"SP"

}

}
}

COBOL.

Níveis.


Muito elegante.


Curiosidade

JSON PARSE.

Não cria ponteiros.

Não cria DOM.

Não cria árvore.


Preenche estruturas COBOL.

Diretamente.


Extremamente eficiente.


Performance

Muito boa.


JSON GENERATE.

É rápido.


Muito mais rápido.

Do que escrever.

String manualmente.


Exemplo ruim.

STRING

'{'

'"nome":"'

WS-NOME

'"'

'}'

Terrível.


JSON GENERATE.

Melhor.


Quando usar?

Excelente para.


APIs.

REST.

MQ.

Kafka.

OpenShift.

Mobile.

Cloud.

Microsserviços.


Quando evitar?


Arquivos internos.

VSAM.

Batch puro.

Relatórios.


Curiosidade Bellacosa

Muitos programas COBOL modernos já trabalham com JSON diariamente.

E boa parte dos usuários finais jamais imagina.

Ao abrir um aplicativo bancário.

Consultar saldo.

Fazer PIX.

Solicitar empréstimo.

Atualizar cadastro.

Frequentemente existe um programa COBOL recebendo JSON silenciosamente em algum lugar do IBM Z.


O Conselho do Mestre Bellacosa

Durante décadas, COBOL foi visto como uma linguagem presa a cartões perfurados, arquivos sequenciais e relatórios impressos.

JSON mudou essa percepção.

JSON permitiu que programas escritos há décadas conversassem com aplicações móveis, microsserviços em OpenShift, APIs em nuvem e plataformas digitais espalhadas pela galáxia tecnológica.

E talvez essa seja a maior lição desta primeira jornada.

COBOL não precisou deixar de ser COBOL.

Não precisou abandonar sua robustez.

Não precisou reescrever milhões de linhas.

Ele simplesmente aprendeu um novo idioma.

E hoje pode dizer:

Eu ainda sou COBOL.

Ainda processo milhões de transações por segundo.

Ainda executo no IBM Z.

Mas agora também falo JSON.

E posso conversar com praticamente qualquer sistema da galáxia.


Continua na Parte 2

JSON PARSE – Transformando Texto em Estruturas COBOL: Arrays, Objetos Aninhados, OCCURS, Tratamento de Erros e o Lado Sombrio dos Payloads Maliciosos.


terça-feira, 9 de julho de 2024

COBOL Ponteiros de Memória: Os Cristais Kyber Escondidos do IBM Z – O Padawan Avançado - Parte IV

 

Bellacosa Mainframe e os ponteiros de memoria em cobol Parte IV

COBOL Ponteiros de Memória: Os Cristais Kyber Escondidos do IBM Z

Parte 4 – O Padawan Avançado

COBOL, Metal C, APIs, Buffers Compartilhados, JSON, MQ e as Técnicas Jedi de Alto Desempenho no IBM Z

Por Bellacosa Mainframe


"O Padawan aprende MOVE. O Cavaleiro aprende BASED. O Mestre aprende que um ponteiro pode conectar universos inteiros."

Mestre Bellacosa Sysprog Jedi


Introdução

Chegamos ao último módulo do Holocron dos Ponteiros COBOL.

Nas partes anteriores aprendemos:

Parte 1

  • USAGE POINTER

  • ADDRESS OF

  • SET

  • AMODE

  • Heap

  • Stack

Parte 2

  • BASED

  • ALLOCATE

  • FREE

  • CEEGTST

  • Estruturas dinâmicas

Parte 3

  • SOC4

  • Memory Leak

  • Overlay

  • CEEDUMP

  • IPCS

  • Fault Analyzer

O jovem Padawan então pergunta:

Mestre...

Eu entendi os ponteiros.

Mas onde eles realmente são usados?

O mestre aponta para um gigantesco IBM z17.

E responde.

Em praticamente todos os lugares importantes.


O grande segredo

Poucos desenvolvedores percebem.

Mas produtos IBM utilizam ponteiros intensivamente.

Exemplos.

CICS

DB2

MQ

LE

z/OS

TCP/IP

JES2

JES3

RACF

SMF

VSAM

IMS

Todos.


O COBOL moderno

COBOL não vive sozinho.

Ele conversa.

Com:

C

Metal C

Assembler

Java

MQ

JSON

REST

Sockets


E o idioma dessa conversa é.

Ponteiros.


COBOL e C

Talvez seja o casamento mais comum.


C

Produz buffer.


COBOL

Consome.


Arquitetura.

C


↓

malloc()


↓

PTR



↓

COBOL


BASED

Exemplo conceitual

Programa C.

malloc(1024);

Retorna.

Endereço.


COBOL.

01 WS-PTR POINTER.

Recebe.


Associa.

SET ADDRESS OF BUFFER

TO WS-PTR

Pronto.


COBOL agora enxerga.

Memória criada em C.


Metal C

Mais interessante.


Executa próximo do hardware.


Pode usar.

64 bits.

Storage Keys.


Compartilhar.

Buffers.


Muito utilizado.

Middleware.


Shared Memory

Outro uso avançado.


Vários programas.

Mesmo buffer.


Visualmente.

Programa A


↓

Shared Buffer


↑


Programa B

Sem cópia.


Muito rápido.


MQ

Excelente exemplo.


MQGET

MQPUT


Mensagem.


Buffer.


COBOL.

Ponteiro.


Estrutura BASED.


Visualmente.

MQ


↓

Buffer


↓

PTR


↓

BASED

Processamento.

Zero cópia.


JSON

Muito utilizado hoje.


Imagine.

{
"name":"Bellacosa",

"idade":52
}

Parser.

Cria árvore.


Cada nó.

Possui ponteiros.


Pai.

Filho.

Irmão.


Exemplo.

JSON ROOT


↓


name


↓


idade

XML

Mesma ideia.


DOM.


Tree.


Ponteiros ligam.

Nós.


APIs

z/OS Connect.


Buffers.


Payload.


Parser.


Muito comum.


Sockets

TCP/IP.


Recebe.

4096 bytes.


Ponteiro.


COBOL lê.


Mais eficiente.


Cache

Outro caso.


Tabela gigante.


Ponteiro.

Evita copiar.


Exemplo.

100 MB.


Mover.

Custa.


Apontar.

8 bytes.


Quase instantâneo.


Tabelas in-memory

Excelente.


DB local.


Lookup rápido.


Hash.


B-tree.


Implementável.


Estruturas avançadas

Lista Duplamente Encadeada

NODE


PREV


NEXT

Árvore AVL


Balanceada.


Ponteiros.


B-tree

Muito utilizada.

Banco dados.


Grafo

Exemplo.

A


/ \


B  C


\ /


D

Tudo possível.


Comparação com outras linguagens

LinguagemPonteiros
COBOLSim
CSim
C++Sim
RustControlado
JavaReferências
GoSim
PythonOculto

Curiosidade

Java.

Esconde.


COBOL.

Mostra.


C.

Expõe totalmente.


Rust.

Protege.


Quando usar?

Bellacosa recomenda.


Excelente.

Buffers

MQ

JSON

XML

APIs

Cache

LE

Middleware

Parsers

Estruturas dinâmicas


Quando evitar?

Cadastro.


Folha pagamento.


VSAM simples.


DB2 comum.


Relatórios.


Performance

Muito alta.


Sem MOVE.


Sem COPY.


Sem serialização.


Muito usada.

Em produtos IBM.


Segurança

Ainda importante.


Ponteiro errado.

Continua.

SOC4.


Heap inválido.


Overlay.


Corrompe.


Documentação

Obrigatória.


Desenhe.

Diagramas.


Exemplo.

PTR1


↓

NODE1


↓

NODE2


↓

NODE3

Ajuda manutenção.


Bellacosa Best Practices

Regra 1

Inicialize.

Sempre.

SET PTR TO NULL

Regra 2

Documente.


Regra 3

Libere.


Regra 4

Nunca reutilize.

Após FREE.


Regra 5

BASED bem definido.


Regra 6

Evite engenharia excessiva.


O Teste do Mestre

Pergunta ao Padawan.

Você precisa.

Criar.

Lista encadeada?


Não?


Use OCCURS.


Sim?


Use ponteiros.


Curiosidades Finais

A maioria dos desenvolvedores COBOL jamais precisará escrever uma árvore AVL.

Ou um parser XML próprio.

Ou um cache compartilhado.

Ou uma estrutura dinâmica baseada em CEEGTST.

Mas os profissionais que sabem fazer isso normalmente pertencem a grupos bastante especializados:

  • Sysprogs

  • Middleware Engineers

  • Desenvolvedores CICS

  • Equipes MQ

  • Produtos IBM

  • Desenvolvedores de Frameworks

  • Especialistas em LE

  • Equipes de Modernização IBM Z


O Conselho Final do Mestre Bellacosa

Os ponteiros em COBOL são quase como cristais Kyber escondidos em uma antiga câmara do templo IBM Z.

Durante décadas, muitos desenvolvedores passaram por eles sem percebê-los.

Outros ouviram histórias assustadoras sobre SOC4, overlays e memory leaks e decidiram nunca tocá-los.

E alguns poucos escolheram estudá-los profundamente.

Esses poucos descobriram algo fascinante.

Ponteiros não servem apenas para criar problemas.

Eles são a base invisível que sustenta grande parte das tecnologias modernas do ecossistema IBM Z.

São eles que permitem compartilhar buffers entre linguagens.

São eles que fazem parsers navegarem por documentos JSON gigantescos.

São eles que ajudam produtos IBM a movimentar milhões de mensagens MQ por segundo.

São eles que transformam estruturas estáticas em sistemas vivos, capazes de crescer, adaptar-se e responder dinamicamente às necessidades do negócio.

Mas existe uma última lição.

Talvez a mais importante.

Um ponteiro não possui moral.

Ele não distingue sabedoria de imprudência.

Ele apenas aponta.

E cabe ao desenvolvedor decidir se está usando esse poder para construir um elegante mecanismo de alto desempenho ou para abrir um portal direto para um CEEDUMP de 500 páginas às três horas da manhã de um fechamento bancário.


Fim do Holocron Bellacosa Mainframe

COBOL Ponteiros de Memória: Os Cristais Kyber Escondidos do IBM ZParte 1 a Parte 4 concluídas.


segunda-feira, 15 de abril de 2024

COBOL Ponteiros de Memória: Os Cristais Kyber Escondidos do IBM Z – O Despertar da Força dos Ponteiros - Parte I

 

Bellacosa Mainframe e os ponteiros de memoria no COBOL Parte I

COBOL Ponteiros de Memória: Os Cristais Kyber Escondidos do IBM Z

Parte 1 – O Despertar da Força dos Ponteiros

Quando o Padawan Descobre que um Endereço Pode Ser Mais Poderoso que os Dados

Por Bellacosa Mainframe


"O dado é importante. Mas conhecer onde ele vive na memória é conhecer a própria Força."

Mestre Sysprog Bellacosa


Introdução

Existe um momento na jornada de todo desenvolvedor COBOL em que ele acredita já ter visto praticamente tudo.

Aprendeu arquivos.

Aprendeu VSAM.

Aprendeu DB2.

Aprendeu CICS.

Aprendeu tabelas OCCURS.

Aprendeu REDEFINES.

Aprendeu recursão.

Aprendeu programas aninhados.

Aprendeu até THREADSAFE.

Então um dia aparece um código semelhante a este:

01 PTR-CLIENTE      USAGE POINTER.

SET PTR-CLIENTE TO ADDRESS OF WS-CLIENTE.

O jovem Padawan olha para aquilo e pergunta:

Mestre…

COBOL tem ponteiros?

O mestre sorri.

Toma um gole de café.

E responde:

Sim.

E são provavelmente uma das funcionalidades menos conhecidas, mais poderosas e potencialmente mais perigosas disponíveis no IBM Enterprise COBOL.


O grande mito

Existe um mito muito comum.

"COBOL não trabalha com endereços."

Errado.

COBOL trabalha.

Sempre trabalhou.

Só que de forma extremamente controlada.

Enquanto linguagens como C permitem brincar livremente com memória:

int *p;

COBOL diz:

Jovem Padawan...

Se você vai manipular memória...

Faça isso com respeito.


O que é um ponteiro?

Um ponteiro não é um dado.

Ele não contém um nome.

Ele não contém um CPF.

Ele não contém uma data.

Ele contém:

O endereço onde algo está.

Imagine.

Apartamento:

Rua Jedi 500

Apartamento 1001

O apartamento é o dado.

O endereço é o ponteiro.


Exemplo.

Cliente

Nome

Bellacosa

Está armazenado em:

7FFF012345678

O ponteiro guarda:

7FFF012345678

Nada mais.


Por que isso existe?

Porque às vezes queremos acessar memória dinamicamente.

Criar estruturas.

Buffers.

Caches.

Árvores.

Filas.

Listas.

Comunicar com C.

Trabalhar com APIs.

Manipular XML.

Shared Memory.

LE Runtime.


COBOL sempre teve ponteiros?

Não.

COBOL 60

Não.

COBOL 68

Não.

COBOL 74

Não.


A situação começou a mudar com:

COBOL 85


Mais tarde.

IBM Enterprise COBOL.

Introduziu:

USAGE POINTER

ADDRESS OF

BASED

ALLOCATE

FREE


Atualmente.

Enterprise COBOL

4

5

6

6.3

6.4

6.5

Suportam totalmente.


O que é USAGE POINTER?

É o tipo especial que armazena um endereço.

Exemplo.

01 WS-PTR.

   USAGE POINTER.

ou

01 WS-PTR POINTER.

Não faça:

PIC X(08)

Errado.


Não faça:

PIC 9(18)

Errado.


O compilador conhece o formato.

Você não precisa.


ADDRESS OF

Talvez seja a instrução mais importante.

Exemplo.

Temos.

01 WS-CLIENTE.

   05 WS-NOME PIC X(30).

Pegando endereço.

SET WS-PTR

TO ADDRESS OF WS-CLIENTE

Pronto.

Agora.

WS-PTR aponta.

Para WS-CLIENTE.


Visualmente

Antes.

WS-PTR


NULL

Depois.

WS-PTR


0000007FFF123450

Como funciona na memória

Imagine.

Working Storage

ENDEREÇO


1000


WS-NOME


Bellacosa



1030


WS-IDADE


52



1035


WS-PTR

Executamos.

SET PTR

TO ADDRESS OF WS-NOME

Resultado.

PTR


1000

O ponteiro virou.

Uma espécie de GPS.


O que é SET?

SET é o comando utilizado.

Para manipular ponteiros.

Exemplo.

SET PTR

TO ADDRESS OF WS-DADOS

Outro.

SET PTR TO NULL

Muito importante.

Sempre inicializar.


Boa prática.

SET PTR TO NULL

No início.


Primeiro exemplo completo

Passo 1

Criar estrutura

WORKING-STORAGE SECTION.


01 WS-CLIENTE.

   05 WS-NOME.

      PIC X(30).



01 WS-PTR

USAGE POINTER.

Passo 2

Preencher

MOVE 'BELLACOSA'

TO WS-NOME

Passo 3

Capturar endereço

SET WS-PTR

TO ADDRESS OF WS-CLIENTE

Passo 4

Display

DISPLAY 'PONTEIRO OK'

Fim.


O que o compilador faz?

Compilador cria.

Variável especial.

Compatível com arquitetura.

31 bits.

64 bits.


Padawan pergunta.

Mestre...

Então é um hexadecimal?

Resposta.

Sim.

Normalmente.


Exemplo.

0000000012345678

IBM Z e endereçamento

Aqui começa a magia.

IBM Z possui longa história.


AMODE 24

Década 70.

Memória.

16 MB.


AMODE 31

1983

2 GB


AMODE 64

zSeries

Exabytes teóricos.


COBOL acompanha.


Working Storage

Ponteiros podem apontar para:

Working Storage


Local Storage


Heap


Dynamically allocated


LE Areas


Buffers


Stack

Existe outra área.

Stack.

Exemplo.

Função chamada.

STACK



Frame A


Frame B


Frame C

Cada frame.

Possui.

Variáveis.

Retorno.

Contexto.


Ponteiros podem apontar.

Para stack.

Sim.


Mas aqui mora perigo.


O lado sombrio

Imagine.

Procedimento.

Termina.

Stack destruída.


Ponteiro ainda existe.


Aponta.

Para memória inválida.


Chamamos isso.

Dangling Pointer.


Exemplo.

PTR


12345

Memória já morreu.


Resultado.

SOC4.


Heap

Heap é diferente.

Sobrevive.

Mais tempo.


Usado em.

ALLOCATE.

CEEGTST.

GETMAIN.


Mais seguro.


Curiosidade

Muitos programas COBOL bancários.

Nunca usam ponteiros.


Por quê?

Não precisam.


COBOL nasceu.

Para registros.

Arquivos.

Campos fixos.


Ponteiros vieram.

Muito depois.


Vantagens

Extremamente rápidas.

Não copia dados.


Exemplo.

Mover.

1 MB.

Custa.

CPU.


Mover ponteiro.

8 bytes.

Instantâneo.


Onde usar?

Excelente para.

XML

JSON

Árvores

Cache

Filas

MQ

Buffers

APIs

Sockets

C

Metal C


Onde NÃO usar?

Cadastro clientes.

Folha pagamento.

Relatórios.

VSAM simples.

Batch convencional.


Performance

Muito boa.

Quase zero overhead.


Mas.

Erro custa caro.


Um MOVE errado.

Perde registro.


Ponteiro errado.

Pode derrubar programa.


SOC4.


Segurança

Ponteiros são ferramenta poderosa.

Mas perigosos.


Podem causar.

Corrupção memória.

Exposição dados.

Abends.

Memory leaks.


Padawan deve lembrar.

Ponteiro não sabe.

Se memória ainda existe.

Ele apenas acredita.


Curiosidades Bellacosa

Pouquíssimos desenvolvedores COBOL escrevem código com ponteiros diariamente.

Mas os profissionais que trabalham com:

  • Language Environment

  • XML parsers

  • CEEGTST

  • Metal C

  • DB2 internals

  • Middleware

  • MQ exits

  • CICS User Exits

  • z/OS Connect

  • Parsers de alta performance

frequentemente encontram USAGE POINTER, ADDRESS OF, BASED e estruturas dinâmicas escondidas em programas aparentemente inocentes.


O Conselho do Mestre Bellacosa

Imagine que os dados COBOL são sabres de luz.

Você pode segurá-los diretamente.

Pode copiá-los.

Pode movê-los.

Pode validá-los.

Mas um ponteiro é diferente.

Um ponteiro é um mapa para encontrar o sabre.

Ele não contém energia.

Ele não contém plasma.

Ele apenas diz:

"Vá até aquele lugar da memória e você encontrará aquilo que procura."

E essa é justamente a beleza e o perigo dos ponteiros em COBOL.

Eles permitem que o Padawan transcenda a programação tradicional baseada em registros fixos e passe a manipular a própria estrutura da memória do IBM Z.

Mas também ensinam uma das maiores lições do universo mainframe:

O dado pode estar protegido por RACF.

O dataset pode estar catalogado.

O programa pode ser RENT e THREADSAFE.

Mas um ponteiro errado continua tendo o poder de levar até mesmo um Mestre Sysprog ao temido S0C4.

Continua na Parte 2 – BASED, ALLOCATE, CEEGTST e Estruturas Dinâmicas: Construindo Listas Encadeadas no IBM Z.


terça-feira, 26 de março de 2024

COBOL Multithread no Mainframe: O Lado Quântico da Força no IBM Z

Bellacosa Mainframe e o cobol multithread

COBOL Multithread no Mainframe: O Lado Quântico da Força no IBM Z

Quando o Padawan Descobre que um Programa COBOL Pode Executar Várias Trilhas de Execução Simultaneamente

Por Bellacosa Mainframe

"Seu pai conhecia uma técnica chamada multithreading. Era um poderoso aliado do lado luminoso da CPU, antes que o excesso de serialização o consumisse."

Mestre Sysprog Bellacosa


A Pergunta que Todo Padawan COBOL Faz

Após aprender:

  • CALL

  • Nested Programs

  • Recursividade

  • LE

  • RENT

  • THREADSAFE

surge uma dúvida inevitável.

Mestre...

Um programa COBOL pode criar Threads?

A resposta curta é:

Sim.

Mas...

Não da forma que Java, C++ ou Python fazem.

E aqui começa uma das partes mais interessantes da arquitetura IBM Z.


O mito do COBOL Monothread

Durante décadas, COBOL foi praticamente sinônimo de:

Uma tarefa

↓

Um programa

↓

Um fluxo

↓

Fim

Exemplo:

OPEN

PERFORM

READ

UPDATE

WRITE

CLOSE

STOP RUN

Linear.

Sequencial.

Determinístico.


Era suficiente.

Bancos.

Seguros.

Governo.

Folha pagamento.


Mas IBM Z mudou

Hoje temos:

LPARs

SMT

zIIP

SRB

TCB

OpenMP

POSIX

USS

Java

C++

Metal C

E COBOL começou a participar desse universo.


A resposta correta

Pergunta:

COBOL possui

CREATE THREAD

Não.

Não possui.


Pergunta:

COBOL pode executar multithread?

Sim.

Através do ambiente.


Onde isso é possível?

Basicamente.

USS

Unix System Services


LE

Language Environment


POSIX

pthread


CICS THREADSAFE


Java Integration

JNI


Metal C


Quando surgiu?

LE apareceu.

Década 90.

Posix Threads.

zOS UNIX.

Enterprise COBOL V3.

V4.

V5.

V6.


COBOL 6.5

convive perfeitamente.


O conceito

COBOL não cria.

COBOL participa.


Exemplo.

C cria.

COBOL executa.


Arquitetura

Programa Mestre


↓

pthread_create()


↓

Thread A


↓

COBOL


THREAD-CPF




Thread B


↓

COBOL


THREAD-END




Thread C


↓

COBOL


THREAD-PIX

Como funciona na memória

Cada thread possui:

PCB

TCB

Stack

Registers

PSW

LE Context


Exemplo

Thread 1

Stack

64 KB


Thread 2

64 KB


Thread 3

64 KB


Visualmente

MEMÓRIA



THREAD 1


STACK



THREAD 2


STACK



THREAD 3


STACK




HEAP



SHARED

O ponteiro de execução

Aqui está a magia.

Cada thread possui.

Instruction Pointer

PSW

Program Counter


Exemplo

Thread 1

EXECUTANDO


Linha 500

Thread 2

Linha 200

Thread 3

Linha 950

Todos simultaneamente.


CPU troca.

Dispatch.

Redispatch.


O Scheduler

zOS decide.

Não COBOL.


WLM.

Gerencia.

Prioridade.

Classe.

Importância.


Exemplo real

Sistema anti-fraude.


Thread 1

CPF


Thread 2

PIX


Thread 3

Cartão


Thread 4

IA


Programa pai espera.


Como esperar

Join.


Exemplo conceitual

THREAD CREATE


THREAD CREATE


THREAD CREATE



WAIT

COBOL recebe resultado.


Exemplo com C

Programa C

pthread_create();

Chama COBOL

THREADCPF

COBOL

PROGRAM-ID. THREADCPF.

Executa.


Retorna.


Pode fazer COBOL puro?

Praticamente não.


Enterprise COBOL

não possui.

START THREAD

Não existe.


Alternativa elegante

Múltiplas subtarefas

Batch.


Exemplo.

JOB

STEP1


STEP2


STEP3

Executando em paralelo.


JES2.


Muito usado.


Outra alternativa

CICS

THREADSAFE


Exemplo

Programa

THREADSAFE


Múltiplas tasks.


CICS gerencia.


THREADSAFE

Extremamente importante.


Programa comum

QR TCB


THREADSAFE

L8

T8


Múltiplas CPUs.


Maior throughput.


Cuidados

Working Storage

Perigoso.


Thread 1

WS=100


Thread 2

WS=500


Corrupção.


Melhor

LOCAL STORAGE


Exemplo

LOCAL-STORAGE SECTION.

Cada thread

sua cópia.


Reentrância

Obrigatório.


Programa

RENT


ou

REENTRANT

Sem isso.

Desastre.


Locks

Às vezes necessários.


Variável compartilhada.


Thread 1

incrementa


Thread 2

incrementa


Resultado errado.


Exemplo

100

esperado


Recebe

98


Race condition.


Segurança

Ataques possíveis.


Deadlock.


Starvation.


Race.


Stack exhaustion.


DoS.


Exemplo

Thread A

espera B


B espera C


C espera A

Fim.


Parado.


Performance

Depende.


CPU bound

Excelente.


I/O bound

Média.


DB2

Depende.


VSAM

Depende.


Locking.


zIIP

Grande vantagem.


LE

Java

XML

podem usar.


Economia MIPS.


Curiosidade

Maioria dos programas COBOL bancários.

Ainda.

Monothread.


Porque.

São rápidos.

Determinísticos.

Confiáveis.


Exemplo Arquitetura Moderna

MASTER


│


├── Thread CPF


├── Thread PIX


├── Thread AML


├── Thread IA


└── Thread LOG

Master acompanha.


Tabela.

THREAD-ID


STATUS


RC

Exemplo

001


RUNNING


002


ENDED


003


WAIT

Master coleta.


Merge.


Retorna.


Pode valer a pena?

Sim.

Análise fraude.

OCR.

JSON.

IA.

APIs.

Criptografia.

Scoring.


Não.

Leitura sequencial.

Sort.

Folha pagamento.

Batch tradicional.


O conselho do Mestre Bellacosa

Multithreading em COBOL no IBM Z é quase como pilotar um caça estelar experimental escondido em um hangar do datacenter. O motor existe, a tecnologia é impressionante, mas ela não foi colocada diretamente no painel de instrumentos do programador COBOL.

O COBOL clássico continua sendo uma linguagem essencialmente sequencial. Entretanto, quando combinado com Language Environment, POSIX Threads, USS, CICS THREADSAFE, Java ou Metal C, ele passa a habitar um universo onde dezenas de trilhas de execução podem coexistir dentro do mesmo endereço de memória, cada uma com seu próprio stack, contexto LE, PSW e ponteiro de instrução.

O verdadeiro Padawan precisa entender uma lição importante:

O programa COBOL não é o Mestre dos Threads.

Ele é um guerreiro altamente especializado convocado para executar missões dentro de um ecossistema que o IBM Z já domina há décadas.

E talvez essa seja a maior beleza do mainframe moderno: ele consegue executar milhões de transações por segundo, milhares de tarefas concorrentes e dezenas de linguagens diferentes, enquanto um antigo programa COBOL escrito há trinta anos continua processando registros tranquilamente, como um velho Mestre Jedi que já viu muitas gerações de processadores nascerem e desaparecerem na galáxia IBM Z.


quarta-feira, 28 de fevereiro de 2024

Programas COBOL Aninhados: Os Holocrons Secretos Escondidos Dentro de um Único Load Module

 

Bellacosa Mainframe e o caso do programa COBOL com varios pgms aninhados

Programas COBOL Aninhados: Os Holocrons Secretos Escondidos Dentro de um Único Load Module

Quando o Padawan Descobre que um Programa COBOL Pode Conter Outros Programas COBOL em Seu Interior

Por Bellacosa Mainframe

"Nem todo programa precisa viver sozinho. Alguns mestres escondem seus aprendizes dentro do próprio templo."

Mestre Bellacosa Sysprog Jedi

Durante décadas, boa parte dos desenvolvedores COBOL aprendeu uma arquitetura bastante simples:

Programa A

CALL Programa B

CALL Programa C

GOBACK

Fim.

Era o modelo clássico.

Cada programa em um membro.

Cada módulo separado.

Cada compilação independente.

Cada load module vivendo sua própria vida no PDS ou PDSE.

Mas então o jovem Padawan encontra algo estranho em um código legado:

IDENTIFICATION DIVISION.
PROGRAM-ID. CLIENTES.

...

IDENTIFICATION DIVISION.
PROGRAM-ID. VALIDA-CPF.

...

IDENTIFICATION DIVISION.
PROGRAM-ID. CALCULA-IDADE.

Ele arregala os olhos.

Pensa:

Mestre...

Tem três programas no mesmo fonte...

Isso é magia negra?

Não.

É COBOL.

E existe há muito tempo.

Poucos desenvolvedores modernos utilizam essa funcionalidade.

Menos ainda entendem completamente como ela funciona.

E alguns veteranos passam a carreira inteira sem escrever um único programa aninhado.

Hoje vamos abrir esse antigo holocron.


O que é um Programa Aninhado?

Em COBOL, um programa pode conter outros programas.

Algo semelhante a:

Programa principal

  • Programa filho A

  • Programa filho B

  • Programa filho C

Tudo dentro do mesmo fonte.

Exemplo:

PROGRAMA PRINCIPAL


PROGRAMA FILHO


PROGRAMA NETO

Hierarquia.

Muito parecido com:

Java

Inner Class

Python

Nested Function

Pascal

Nested Procedures

COBOL possui conceito semelhante.


Quando Surgiu?

Programas aninhados apareceram nas especificações modernas do COBOL.

Principalmente:

COBOL 85

Posteriormente aprimorados em:

Enterprise COBOL V3

V4

V5

V6

Hoje são totalmente suportados.

COBOL 6.5

IBM z16

IBM z17


Estrutura Básica

Exemplo.

Programa Principal

IDENTIFICATION DIVISION.
PROGRAM-ID. CLIENTE.

Programa interno

IDENTIFICATION DIVISION.
PROGRAM-ID. VALIDA.

Outro

IDENTIFICATION DIVISION.
PROGRAM-ID. CALCULA.

Tudo junto.


Exemplo Completo

Programa Pai

IDENTIFICATION DIVISION.
PROGRAM-ID. CLIENTE.


DATA DIVISION.


WORKING-STORAGE SECTION.


01 WS-CPF.
PIC X(11).



PROCEDURE DIVISION.


MOVE '12345678901'
TO WS-CPF


CALL 'VALIDA'


DISPLAY "FIM"



STOP RUN.

Programa Filho

IDENTIFICATION DIVISION.
PROGRAM-ID. VALIDA.


PROCEDURE DIVISION.


DISPLAY 'VALIDANDO'


EXIT PROGRAM.

Fim.


Exemplo Realista

Vamos construir.

Sistema cadastro.

Programa principal

CADASTRO

Filhos

VALIDA-CPF

VALIDA-DATA

CALCULA-IDADE

GERA-LOG


Passo 1

Programa principal

PROGRAM-ID. CADASTRO.

Passo 2

WS

01 WS-CPF.
01 WS-DATA.
01 WS-IDADE.

Passo 3

Chamar programas internos

CALL 'VALIDA-CPF'

CALL 'VALIDA-DATA'

CALL 'CALCULA-IDADE'

Passo 4

Definir programa interno

IDENTIFICATION DIVISION.
PROGRAM-ID. VALIDA-CPF.

Passo 5

Lógica

IF CPF NUMERIC

DISPLAY 'OK'

ELSE

DISPLAY 'ERRO'

Passo 6

Encerrar

EXIT PROGRAM.

Passo 7

Novo programa

PROGRAM-ID. CALCULA-IDADE.

Tudo dentro do mesmo fonte.


Como COBOL Enxerga Isso?

COBOL vê:

Programa Pai

Programa Filho

Programa Neto

Estrutura hierárquica.


Como é Chamado?

Nested Program

Programa Interno

Contained Program

Outer Program

Inner Program


Como Funciona na Memória?

Aqui a magia começa.

Suponha:

CADASTRO

contém

VALIDA

contém

LOG


Carregamento

LOAD MODULE


CADASTRO


VALIDA


LOG

Tudo junto.

Mesmo módulo.


Não existe:

Busca catálogo

Load library

Fetch

Link

Já está residente.


Vantagem

Muito rápida.


Visualmente

Programa separado

CALL


LOAD


FETCH


EXECUTA

Programa interno

CALL


EXECUTA

Menos overhead.


Compartilhamento de Variáveis

Esse é o recurso mais poderoso.

Programa interno pode acessar dados externos.

Exemplo

Programa pai

01 WS-NOME.
PIC X(30).

Filho

DISPLAY WS-NOME.

Sem USING.

Sem linkage.

Sem parâmetro.

Sem copiar.


Mágica?

Não.

Escopo léxico.


Exemplo

Pai

MOVE 'BELLACOSA'

TO WS-NOME

Filho

DISPLAY WS-NOME

Resultado

BELLACOSA

Por Que Isso Existe?

Reduzir acoplamento.

Criar rotinas privadas.

Encapsulamento.

Organização.


É semelhante a:

Método privado Java

Função interna Python

Classe interna


Curiosidade

Muitos programadores COBOL nem sabem que isso existe.

Porque nos bancos normalmente vemos:

CALL externo

PDS

Loadlib

Arquitetura tradicional.


Exemplo de Encapsulamento

Programa externo

Atendimento.

Internos

Valida

Log

Criptografa

Audita

Ninguém pode chamar diretamente.


Somente programa pai.


Segurança

Excelente vantagem.

Programa externo:

QUALQUER UM CHAMA

Interno

SÓ O PAI CHAMA

Maior controle.


Performance

Muito boa.

Programa já está carregado.

Sem I/O.

Sem busca.

Sem FETCH.


Pode economizar milhares de chamadas.


Existe Desvantagem?

Sim.

Grande.


Fonte gigantesco.

50000 linhas.

100000 linhas.

Difícil manutenção.


Problema do Monstro Cósmico

Exemplo

CADASTRO


VALIDA


IDADE


LOG


EMAIL


TOKEN


PIX


SMS


AUDITORIA


JSON


XML


MQ


DB2

Tudo junto.

Virou um kaiju.


Dificuldade de Reuso

Programa interno não pode ser facilmente reutilizado.

Outro sistema quer usar.

Não consegue.


Terá que copiar.

Ou refatorar.


Debug

Pode confundir.

Call stack enorme.

Nested levels.


IBM Debug Tool ajuda.

Fault Analyzer também.


Cuidados

1 Não exagerar

Máximo recomendado:

3 níveis

Pai

Filho

Neto

Mais que isso:

Dor.


2 Documentar

Quem chama quem.


3 Evitar dependência excessiva

Filho acessando 500 WS.

Ruim.


4 Preferir USING

Mesmo podendo acessar WS externa.

Melhor:

USING WS-CPF

Mais claro.


5 Não esconder regras críticas

Exemplo

Cálculo juros.

Pode dificultar auditoria.


Como Compilar?

Normal.

IGYCRCTL

Enterprise COBOL

Sem segredo.


Compilador entende estrutura.

Gera módulo único.


Programa Recursivo Aninhado

Sim.

É possível.

Filho pode ser:

RECURSIVE


Exemplo

PROGRAM-ID. FATORIAL.


RECURSIVE.

Dentro do pai.


Muito elegante.

Pouco usado.


CALL Estático Interno

Muito eficiente.

CALL 'VALIDA-CPF'

Sem carga.

Sem fetch.


Comparação

CaracterísticaPrograma ExternoPrograma Interno
ReusoExcelenteBaixo
SegurançaMédiaAlta
PerformanceBoaExcelente
EncapsulamentoMédioExcelente
DebugFácilMédio
OrganizaçãoBoaBoa
ManutençãoExcelentePode degradar
DistribuiçãoFácilLimitada

Quando Vale a Pena?

Eu costumo ensinar aos Padawans uma regra simples.

Use programas aninhados quando a rotina fizer sentido apenas dentro daquele programa principal.

Exemplos:

✅ Validação interna

✅ Máscara

✅ Auditoria

✅ Log

✅ Conversão local

✅ Parser pequeno


Evite para:

❌ Acesso DB2

❌ MQ

❌ APIs

❌ Serviços compartilhados

❌ Criptografia corporativa

❌ Regras usadas por dezenas de sistemas


O Conselho Final do Mestre Bellacosa

Programas aninhados em COBOL são quase como compartimentos secretos escondidos em um gigantesco cruzador estelar IBM Z. Eles oferecem encapsulamento, velocidade, organização e um nível de proteção natural contra reutilização indevida.

Mas, assim como qualquer artefato poderoso do universo dos Sysprogs Jedi, devem ser usados com sabedoria.

Um pequeno programa interno de validação pode tornar um sistema elegante e fácil de entender.

Dez programas internos profundamente dependentes das variáveis do pai podem transformar um módulo em um labirinto digno de um antigo datacenter abandonado, onde cada alteração provoca medo, regressões e longas noites analisando dumps.

A filosofia Bellacosa Mainframe é simples:

Aninhe comportamentos, não sistemas inteiros.

Encapsule segredos, não complexidade desnecessária.

E lembre-se sempre: se o Padawan precisar de três cafés, dois dumps e um Fault Analyzer para entender a estrutura do programa, talvez o lado sombrio da manutenção já tenha vencido.


 

segunda-feira, 22 de janeiro de 2024

COBOL Recursivo: Quando o Padawan Descobre que um Programa Pode Invocar a Si Mesmo

 

Bellacosa Mainframe apresenta um programa cobol recursivo

COBOL Recursivo: Quando o Padawan Descobre que um Programa Pode Invocar a Si Mesmo

O Poder Proibido do CALL Infinito na Galáxia IBM Z

Por Bellacosa Mainframe

"O medo leva ao ABEND. O ABEND leva ao dump. O dump leva ao sofrimento."

— Mestre Sysprog Yoda/390

Durante muitos anos, programadores COBOL cresceram acreditando em uma verdade absoluta:

"Programa COBOL não faz recursão."

Era praticamente um dogma do templo Jedi dos mainframes.

E, honestamente?

Durante décadas isso foi quase verdade.

A maioria dos sistemas bancários, seguradoras, governo e processamento batch nunca precisou de algoritmos recursivos.

Mas então surgiram:

  • XML

  • JSON

  • árvores hierárquicas

  • parsers

  • estruturas dinâmicas

  • APIs modernas

  • integração com Java

  • serviços z/OS Connect

E um dia o jovem Padawan perguntou:

"Mestre Bellacosa...

Posso fazer um programa COBOL chamar ele mesmo?"

A resposta é:

Sim.

Mas como todo poder da Força, existe um preço.


O que é Recursividade?

Recursão significa:

Um procedimento invoca ele próprio.

Exemplo clássico:

Calcular fatorial.

5! = 5 × 4 × 3 × 2 × 1

Matematicamente:

Fatorial(n)

se n=1 retorna 1

senão

n * Fatorial(n-1)

Exemplo:

F(5)

5 × F(4)

5 × 4 × F(3)

5 × 4 × 3 × F(2)

5 × 4 × 3 × 2 × F(1)

120

É uma técnica extremamente elegante.


COBOL Sempre Teve Recursão?

Não.

Historicamente COBOL nasceu em 1959.

E sua filosofia era:

Processamento comercial.

Arquivos.

Registros.

Batch.

Volumes enormes.

Não havia necessidade prática.

Durante décadas COBOL assumia:

Programa residente

Uma única Working Storage

Compartilhada

Exemplo:

WORKING-STORAGE SECTION.

01 CONTADOR PIC 9(5).

Só existe uma instância.

Todo mundo usa a mesma.

Problema:

Programa chama ele mesmo.

Segunda chamada sobrescreve variáveis.

Primeira execução quebra.

Caos.


Quando Surgiu?

IBM Enterprise COBOL começou suportar adequadamente recursão através da opção:

RECURSIVE

ou

RENT

Dependendo da geração do compilador.

Hoje encontramos suporte em:

Enterprise COBOL 4

Enterprise COBOL 5

Enterprise COBOL 6.x

COBOL 6.3

COBOL 6.4

COBOL 6.5

Totalmente suportado.

Inclusive no IBM z17.


Como Declarar um Programa Recursivo

No cabeçalho:

IDENTIFICATION DIVISION.
PROGRAM-ID. FATORIAL RECURSIVE.

ou

PROGRAM-ID. FATORIAL.

RECURSIVE.

Depende do compilador.


Exemplo Completo

Passo 1

Definir LINKAGE

LINKAGE SECTION.


01 LK-NUMERO.
   PIC 9(4).

01 LK-RESULTADO.
   PIC 9(10).

Passo 2

Procedure Division

PROCEDURE DIVISION USING
          LK-NUMERO
          LK-RESULTADO.

Passo 3

Caso base

IF LK-NUMERO <= 1

   MOVE 1 TO LK-RESULTADO

ELSE

...

Passo 4

Criar variável local

LOCAL-STORAGE SECTION.


01 WS-TEMP.
   PIC 9(10).

01 WS-N.
   PIC 9(4).

Local Storage é fundamental.

Já veremos por quê.


Passo 5

Preparar próxima chamada

COMPUTE WS-N = LK-NUMERO -1

Passo 6

Invocar a si mesmo

CALL 'FATORIAL'

USING

WS-N
WS-TEMP

Passo 7

Calcular

COMPUTE LK-RESULTADO =
        LK-NUMERO * WS-TEMP

Fim.


Programa Completo

IDENTIFICATION DIVISION.
PROGRAM-ID. FATORIAL RECURSIVE.

DATA DIVISION.


LOCAL-STORAGE SECTION.


01 WS-N.
   PIC 9(4).

01 WS-TEMP.
   PIC 9(10).


LINKAGE SECTION.


01 LK-NUMERO.
   PIC 9(4).

01 LK-RESULTADO.
   PIC 9(10).


PROCEDURE DIVISION USING
        LK-NUMERO
        LK-RESULTADO.


IF LK-NUMERO <= 1

   MOVE 1 TO LK-RESULTADO

ELSE

   COMPUTE WS-N =
           LK-NUMERO -1


   CALL 'FATORIAL'

   USING

      WS-N
      WS-TEMP


   COMPUTE LK-RESULTADO =
           LK-NUMERO * WS-TEMP

END-IF.


GOBACK.

O que Acontece na Memória?

Aqui mora a magia.

Imagine:

FATORIAL(5)

Stack:

Frame 1
n=5

Chama:

Frame 2
n=4

Depois:

Frame 3
n=3

Depois:

Frame 4
n=2

Depois:

Frame 5
n=1

Retorno:

Frame 5 → 1

Frame 4 → 2

Frame 3 → 6

Frame 2 →24

Frame 1 →120


Visualmente

STACK



F(5)

F(4)

F(3)

F(2)

F(1)

Depois:

POP


F(1)


F(2)


F(3)


F(4)


F(5)

O Papel da LOCAL-STORAGE

Muitos Padawans cometem um erro fatal.

Usar:

WORKING-STORAGE

Exemplo:

01 WS-N.

Errado.

Por quê?

Porque Working Storage é única.

Compartilhada.

Exemplo:

Primeira chamada

WS-N=5

Segunda

WS-N=4

Terceira

WS-N=3

Sobrescreve.

Tudo quebra.


LOCAL-STORAGE

Cria uma cópia nova.

Para cada chamada.

Exemplo:

Frame 1

WS-N=5

Frame 2

WS-N=4

Frame 3

WS-N=3

Independentes.


Como o Compilador Faz Isso?

Ele cria activation records.

Também chamados:

Stack frames

Contém:

Variáveis locais

Endereço retorno

Parâmetros

Estado execução

Exatamente igual:

C

C++

Java

Pascal


CALL Estático

Mais eficiente.

CALL 'FATORIAL'

Resolvido no linkedit.

Menos overhead.


CALL Dinâmico

MOVE 'FATORIAL'

TO WS-PGM


CALL WS-PGM

Mais flexível.

Menos rápido.


Existe Limite?

Sim.

STACK.

Região LE.

Memory limits.

Exemplo:

F(1000000)

Boom.

SOC1

SOC4

S878

S80A

Dependendo ambiente.


Como Evitar?

Caso base.

Sempre.

Sempre.

Sempre.

Exemplo ruim:

CALL FATORIAL


CALL FATORIAL


CALL FATORIAL

Nunca termina.


Cuidados Importantes

1 Não usar Working Storage

Errado.


2 Ter condição parada

Obrigatório.


3 Validar entrada

Exemplo:

IF NUMERO < 0

Fatorial negativo?

Não faz sentido.


4 Cuidado com profundidade

100 níveis

Ok.

500

Talvez.

10000

Perigoso.


5 Testar LE Runtime

HEAP

STACK

ALL31

Importante.


Performance

Aqui muitos ficam decepcionados.

Recursão é elegante.

Mas nem sempre rápida.

Cada chamada cria:

Frame

Parâmetros

Contexto

Retorno

Overhead.


Loop tradicional:

PERFORM


UNTIL

Quase sempre vence.


Exemplo

Fatorial iterativo.

MOVE 1 TO WS-TOTAL


PERFORM VARYING I


FROM 1


BY 1


UNTIL I > N


MULTIPLY I


BY WS-TOTAL


END-PERFORM

Muito eficiente.


Quando Vale a Pena?

Árvores.

XML.

JSON.

DOM.

Grafos.

Estruturas hierárquicas.

Menus.

Organogramas.

Filesystem.

Dependências.


Exemplo XML

empresa


 departamento


   funcionario


 departamento


   funcionario

Percorrer árvore.

Recursão fica linda.


Segurança

Sim.

Existe aspecto de segurança.

Ataque:

Stack exhaustion.

Negação de serviço.

DoS.

Programa recebe:

99999999

Explode stack.


Proteção:

IF NIVEL > 1000

DISPLAY "ERRO"

STOP RUN

Debug

Debug recursivo é divertido.

E assustador.

Ferramentas:

IBM Debug Tool

Fault Analyzer

Abend Aid

Mostram:

Call Stack

Frame atual

Parâmetros

Muito útil.


Curiosidades

Poucos sistemas bancários usam recursão pesada.

COBOL nasceu para processamento sequencial.

Por isso muitos programadores veteranos passam décadas sem escrever uma única rotina recursiva.


Outra curiosidade:

COBOL OO suporta métodos recursivos naturalmente.

INVOKE SELF

Também funciona.


Recursão de Cauda (Tail Recursion)

Alguns compiladores modernos fazem otimizações.

Mas COBOL IBM geralmente não realiza Tail Call Optimization de forma agressiva como linguagens funcionais.

Logo:

RETURN F(N-1)

Ainda pode consumir stack.

Não confie nisso.


Padrão Recomendado pelo Mestre Bellacosa

Para o jovem Padawan COBOL, eu costumo ensinar uma regra bastante prática:

Use recursão apenas quando ela deixar a solução mais clara do que um PERFORM VARYING.

Se a lógica for:

  • Fatorial

  • Somatório

  • Contador

Prefira iteração.

Se a lógica envolver:

  • Árvores

  • XML

  • JSON aninhado

  • Catálogos IMS

  • Dependências complexas

  • Estruturas organizacionais

  • Menus multiníveis

Então a recursividade torna-se uma excelente aliada.


Considerações Finais

A recursão em COBOL é quase como encontrar um antigo holocron escondido nos corredores de um datacenter IBM Z.

Muitos veteranos nunca precisaram utilizá-la. Outros a evitam por receio de consumir stack, degradar performance ou provocar abends difíceis de diagnosticar.

No entanto, compreender programas recursivos amplia significativamente o repertório técnico de um desenvolvedor COBOL moderno. Em um mundo onde o mainframe conversa diariamente com APIs REST, processa documentos JSON complexos, integra-se com microsserviços e participa de arquiteturas híbridas, dominar recursividade deixa de ser apenas curiosidade acadêmica e passa a ser uma habilidade estratégica.

O verdadeiro Padawan não utiliza recursão para demonstrar inteligência. Ele a utiliza porque compreende profundamente o problema, conhece os limites da memória, respeita a pilha de execução do Language Environment, escolhe LOCAL-STORAGE sabiamente e sabe exatamente quando um simples PERFORM VARYING é a solução mais elegante.

E essa talvez seja a maior lição do COBOL recursivo:

Nem todo poder disponível deve ser usado. Mas todo poder disponível deve ser compreendido.

No templo Bellacosa Mainframe, conhecer a recursividade significa possuir mais uma ferramenta no cinto utilitário do Sysprog Jedi, pronta para ser acionada quando a missão exigir atravessar estruturas tão profundas quanto os corredores infinitos de uma galáxia IBM Z em plena era do z17.