slidge-whatsapp 0.3.0__cp313-cp313-manylinux_2_36_aarch64.whl → 0.3.1__cp313-cp313-manylinux_2_36_aarch64.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (131) hide show
  1. slidge_whatsapp/event.go +33 -9
  2. slidge_whatsapp/generated/_whatsapp.cpython-313-aarch64-linux-gnu.h +179 -179
  3. slidge_whatsapp/generated/_whatsapp.cpython-313-aarch64-linux-gnu.so +0 -0
  4. slidge_whatsapp/generated/build.py +145 -145
  5. slidge_whatsapp/generated/whatsapp.c +1650 -1650
  6. slidge_whatsapp/generated/whatsapp.go +1032 -1032
  7. slidge_whatsapp/generated/whatsapp.py +1274 -1274
  8. slidge_whatsapp/generated/whatsapp_go.h +179 -179
  9. slidge_whatsapp/go.mod +5 -5
  10. slidge_whatsapp/go.sum +14 -14
  11. slidge_whatsapp/session.go +3 -3
  12. slidge_whatsapp/vendor/github.com/ebitengine/purego/README.md +21 -5
  13. slidge_whatsapp/vendor/github.com/ebitengine/purego/abi_loong64.h +60 -0
  14. slidge_whatsapp/vendor/github.com/ebitengine/purego/cgo.go +1 -1
  15. slidge_whatsapp/vendor/github.com/ebitengine/purego/dlerror.go +1 -1
  16. slidge_whatsapp/vendor/github.com/ebitengine/purego/dlfcn.go +1 -1
  17. slidge_whatsapp/vendor/github.com/ebitengine/purego/dlfcn_netbsd.go +15 -0
  18. slidge_whatsapp/vendor/github.com/ebitengine/purego/dlfcn_nocgo_netbsd.go +9 -0
  19. slidge_whatsapp/vendor/github.com/ebitengine/purego/dlfcn_stubs.s +1 -1
  20. slidge_whatsapp/vendor/github.com/ebitengine/purego/func.go +113 -60
  21. slidge_whatsapp/vendor/github.com/ebitengine/purego/gen.go +6 -0
  22. slidge_whatsapp/vendor/github.com/ebitengine/purego/go_runtime.go +1 -1
  23. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/cgo/dlfcn_cgo_unix.go +2 -2
  24. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/cgo/syscall_cgo_unix.go +2 -2
  25. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/abi_loong64.h +60 -0
  26. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/asm_loong64.s +40 -0
  27. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/callbacks.go +1 -1
  28. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/doc.go +1 -1
  29. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/go_libinit.go +1 -1
  30. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/go_linux_loong64.go +92 -0
  31. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/go_netbsd.go +106 -0
  32. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/go_setenv.go +1 -1
  33. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/go_util.go +1 -1
  34. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/iscgo.go +1 -1
  35. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/libcgo.go +1 -1
  36. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/libcgo_darwin.go +4 -0
  37. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/libcgo_freebsd.go +4 -0
  38. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/libcgo_linux.go +4 -0
  39. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/libcgo_netbsd.go +26 -0
  40. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/netbsd.go +23 -0
  41. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/setenv.go +1 -1
  42. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/symbols.go +11 -1
  43. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/symbols_darwin.go +1 -0
  44. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/symbols_freebsd.go +1 -0
  45. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/symbols_linux.go +1 -0
  46. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/symbols_netbsd.go +30 -0
  47. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/trampolines_loong64.s +71 -0
  48. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/trampolines_stubs.s +5 -1
  49. slidge_whatsapp/vendor/github.com/ebitengine/purego/nocgo.go +1 -1
  50. slidge_whatsapp/vendor/github.com/ebitengine/purego/struct_amd64.go +8 -4
  51. slidge_whatsapp/vendor/github.com/ebitengine/purego/struct_arm64.go +16 -6
  52. slidge_whatsapp/vendor/github.com/ebitengine/purego/struct_loong64.go +190 -0
  53. slidge_whatsapp/vendor/github.com/ebitengine/purego/struct_other.go +6 -2
  54. slidge_whatsapp/vendor/github.com/ebitengine/purego/sys_amd64.s +1 -1
  55. slidge_whatsapp/vendor/github.com/ebitengine/purego/sys_arm64.s +1 -1
  56. slidge_whatsapp/vendor/github.com/ebitengine/purego/sys_loong64.s +96 -0
  57. slidge_whatsapp/vendor/github.com/ebitengine/purego/sys_unix_arm64.s +1 -1
  58. slidge_whatsapp/vendor/github.com/ebitengine/purego/sys_unix_loong64.s +75 -0
  59. slidge_whatsapp/vendor/github.com/ebitengine/purego/syscall.go +6 -3
  60. slidge_whatsapp/vendor/github.com/ebitengine/purego/syscall_cgo_linux.go +3 -3
  61. slidge_whatsapp/vendor/github.com/ebitengine/purego/syscall_sysv.go +13 -10
  62. slidge_whatsapp/vendor/github.com/ebitengine/purego/syscall_windows.go +1 -1
  63. slidge_whatsapp/vendor/github.com/ebitengine/purego/zcallback_amd64.s +2002 -2002
  64. slidge_whatsapp/vendor/github.com/ebitengine/purego/zcallback_arm64.s +4002 -4002
  65. slidge_whatsapp/vendor/github.com/ebitengine/purego/zcallback_loong64.s +4014 -0
  66. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/log.go +1 -0
  67. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/module.go +118 -0
  68. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/upgradetable.go +0 -34
  69. slidge_whatsapp/vendor/go.mau.fi/util/exbytes/string.go +20 -0
  70. slidge_whatsapp/vendor/go.mau.fi/util/exbytes/writer.go +78 -0
  71. slidge_whatsapp/vendor/go.mau.fi/util/exslices/cast.go +42 -0
  72. slidge_whatsapp/vendor/go.mau.fi/util/exslices/chunk.go +28 -0
  73. slidge_whatsapp/vendor/go.mau.fi/util/exslices/deduplicate.go +67 -0
  74. slidge_whatsapp/vendor/go.mau.fi/util/exslices/diff.go +63 -0
  75. slidge_whatsapp/vendor/go.mau.fi/util/exsync/event.go +15 -1
  76. slidge_whatsapp/vendor/go.mau.fi/util/random/string.go +47 -7
  77. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/appstate/decode.go +1 -0
  78. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/appstate/encode.go +34 -0
  79. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/appstate/hash.go +1 -0
  80. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/appstate.go +3 -0
  81. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/armadillomessage.go +1 -2
  82. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/call.go +6 -0
  83. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/errors.go +1 -0
  84. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/group.go +63 -42
  85. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/internals.go +14 -10
  86. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/message.go +45 -18
  87. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/msgsecret.go +23 -0
  88. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/notification.go +5 -1
  89. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/pair.go +3 -7
  90. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waAICommon/WAAICommon.pb.go +7747 -0
  91. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/{waBotMetadata/WABotMetadata.proto → waAICommon/WAAICommon.proto} +269 -9
  92. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waDeviceCapabilities/WAProtobufsDeviceCapabilities.pb.go +128 -14
  93. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waDeviceCapabilities/WAProtobufsDeviceCapabilities.proto +10 -0
  94. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waE2E/WAWebProtobufsE2E.pb.go +3236 -4732
  95. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waE2E/WAWebProtobufsE2E.proto +125 -273
  96. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waHistorySync/WAWebProtobufsHistorySync.pb.go +11 -2
  97. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waHistorySync/WAWebProtobufsHistorySync.proto +1 -0
  98. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waStatusAttributions/WAStatusAttributions.pb.go +220 -81
  99. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waStatusAttributions/WAStatusAttributions.proto +13 -0
  100. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waSyncAction/WASyncAction.pb.go +705 -449
  101. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waSyncAction/WASyncAction.proto +23 -0
  102. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWa6/WAWebProtobufsWa6.pb.go +78 -24
  103. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWa6/WAWebProtobufsWa6.proto +6 -0
  104. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWeb/WAWebProtobufsWeb.pb.go +516 -267
  105. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWeb/WAWebProtobufsWeb.proto +22 -0
  106. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/receipt.go +2 -0
  107. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/request.go +4 -0
  108. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/retry.go +2 -3
  109. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/send.go +110 -28
  110. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/clientpayload.go +1 -1
  111. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/noop.go +12 -0
  112. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/lidmap.go +82 -4
  113. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/store.go +112 -55
  114. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/00-latest-schema.sql +8 -7
  115. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/11-redacted-phone-contacts.sql +2 -0
  116. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/store.go +20 -0
  117. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/call.go +6 -5
  118. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/message.go +7 -1
  119. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/user.go +3 -0
  120. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/user.go +31 -2
  121. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/filedesc/desc.go +35 -17
  122. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/filedesc/desc_init.go +14 -0
  123. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/filedesc/desc_lazy.go +20 -0
  124. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/version/version.go +1 -1
  125. slidge_whatsapp/vendor/modules.txt +8 -6
  126. {slidge_whatsapp-0.3.0.dist-info → slidge_whatsapp-0.3.1.dist-info}/METADATA +1 -1
  127. {slidge_whatsapp-0.3.0.dist-info → slidge_whatsapp-0.3.1.dist-info}/RECORD +130 -106
  128. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waBotMetadata/WABotMetadata.pb.go +0 -5156
  129. {slidge_whatsapp-0.3.0.dist-info → slidge_whatsapp-0.3.1.dist-info}/WHEEL +0 -0
  130. {slidge_whatsapp-0.3.0.dist-info → slidge_whatsapp-0.3.1.dist-info}/entry_points.txt +0 -0
  131. {slidge_whatsapp-0.3.0.dist-info → slidge_whatsapp-0.3.1.dist-info}/licenses/LICENSE +0 -0
@@ -13,6 +13,8 @@ import (
13
13
  "fmt"
14
14
  "time"
15
15
 
16
+ "github.com/rs/zerolog"
17
+
16
18
  "go.mau.fi/whatsmeow/appstate"
17
19
  waBinary "go.mau.fi/whatsmeow/binary"
18
20
  "go.mau.fi/whatsmeow/proto/waE2E"
@@ -110,6 +112,7 @@ func (cli *Client) filterContacts(mutations []appstate.Mutation) ([]appstate.Mut
110
112
  }
111
113
 
112
114
  func (cli *Client) dispatchAppState(ctx context.Context, mutation appstate.Mutation, fullSync bool, emitOnFullSync bool) {
115
+ zerolog.Ctx(ctx).Trace().Any("mutation", mutation).Msg("Dispatching app state mutation")
113
116
  dispatchEvts := !fullSync || emitOnFullSync
114
117
 
115
118
  if mutation.Operation != waServerSync.SyncdMutation_SET {
@@ -22,7 +22,7 @@ import (
22
22
  "go.mau.fi/whatsmeow/types/events"
23
23
  )
24
24
 
25
- func (cli *Client) handleDecryptedArmadillo(ctx context.Context, info *types.MessageInfo, decrypted []byte, retryCount int) (handled, handlerFailed bool) {
25
+ func (cli *Client) handleDecryptedArmadillo(ctx context.Context, info *types.MessageInfo, decrypted []byte, retryCount int) (handlerFailed bool) {
26
26
  dec, err := decodeArmadillo(decrypted)
27
27
  if err != nil {
28
28
  cli.Log.Warnf("Failed to decode armadillo message from %s: %v", info.SourceString(), err)
@@ -41,7 +41,6 @@ func (cli *Client) handleDecryptedArmadillo(ctx context.Context, info *types.Mes
41
41
  if dec.Message != nil || dec.FBApplication != nil {
42
42
  handlerFailed = cli.dispatchEvent(&dec)
43
43
  }
44
- handled = true
45
44
  return
46
45
  }
47
46
 
@@ -29,6 +29,12 @@ func (cli *Client) handleCallEvent(node *waBinary.Node) {
29
29
  CallID: cag.String("call-id"),
30
30
  GroupJID: cag.OptionalJIDOrEmpty("group-jid"),
31
31
  }
32
+ if basicMeta.CallCreator.Server == types.HiddenUserServer {
33
+ basicMeta.CallCreatorAlt = cag.OptionalJIDOrEmpty("caller_pn")
34
+ } else {
35
+ // This may not actually exist
36
+ basicMeta.CallCreatorAlt = cag.OptionalJIDOrEmpty("caller_lid")
37
+ }
32
38
  switch child.Tag {
33
39
  case "offer":
34
40
  cli.dispatchEvent(&events.CallOffer{
@@ -145,6 +145,7 @@ var (
145
145
  ErrOriginalMessageSecretNotFound = errors.New("original message secret key not found")
146
146
  ErrNotEncryptedReactionMessage = errors.New("given message isn't an encrypted reaction message")
147
147
  ErrNotEncryptedCommentMessage = errors.New("given message isn't an encrypted comment message")
148
+ ErrNotSecretEncryptedMessage = errors.New("given message isn't a secret encrypted message")
148
149
  ErrNotPollUpdateMessage = errors.New("given message isn't a poll update message")
149
150
  )
150
151
 
@@ -493,8 +493,8 @@ func (cli *Client) JoinGroupWithLink(code string) (types.JID, error) {
493
493
  }
494
494
 
495
495
  // GetJoinedGroups returns the list of groups the user is participating in.
496
- func (cli *Client) GetJoinedGroups() ([]*types.GroupInfo, error) {
497
- resp, err := cli.sendGroupIQ(context.TODO(), iqGet, types.GroupServerJID, waBinary.Node{
496
+ func (cli *Client) GetJoinedGroups(ctx context.Context) ([]*types.GroupInfo, error) {
497
+ resp, err := cli.sendGroupIQ(ctx, iqGet, types.GroupServerJID, waBinary.Node{
498
498
  Tag: "participating",
499
499
  Content: []waBinary.Node{
500
500
  {Tag: "participants"},
@@ -510,6 +510,8 @@ func (cli *Client) GetJoinedGroups() ([]*types.GroupInfo, error) {
510
510
  }
511
511
  children := groups.GetChildren()
512
512
  infos := make([]*types.GroupInfo, 0, len(children))
513
+ var allLIDPairs []store.LIDMapping
514
+ var allRedactedPhones []store.RedactedPhoneEntry
513
515
  for _, child := range children {
514
516
  if child.Tag != "group" {
515
517
  cli.Log.Debugf("Unexpected child in group list response: %s", child.XMLString())
@@ -519,8 +521,19 @@ func (cli *Client) GetJoinedGroups() ([]*types.GroupInfo, error) {
519
521
  if parseErr != nil {
520
522
  cli.Log.Warnf("Error parsing group %s: %v", parsed.JID, parseErr)
521
523
  }
524
+ lidPairs, redactedPhones := cli.cacheGroupInfo(parsed, true)
525
+ allLIDPairs = append(allLIDPairs, lidPairs...)
526
+ allRedactedPhones = append(allRedactedPhones, redactedPhones...)
522
527
  infos = append(infos, parsed)
523
528
  }
529
+ err = cli.Store.LIDs.PutManyLIDMappings(ctx, allLIDPairs)
530
+ if err != nil {
531
+ cli.Log.Warnf("Failed to store LID mappings from joined groups: %v", err)
532
+ }
533
+ err = cli.Store.Contacts.PutManyRedactedPhones(ctx, allRedactedPhones)
534
+ if err != nil {
535
+ cli.Log.Warnf("Failed to store redacted phones from joined groups: %v", err)
536
+ }
524
537
  return infos, nil
525
538
  }
526
539
 
@@ -572,6 +585,37 @@ func (cli *Client) GetGroupInfo(jid types.JID) (*types.GroupInfo, error) {
572
585
  return cli.getGroupInfo(context.TODO(), jid, true)
573
586
  }
574
587
 
588
+ func (cli *Client) cacheGroupInfo(groupInfo *types.GroupInfo, lock bool) ([]store.LIDMapping, []store.RedactedPhoneEntry) {
589
+ participants := make([]types.JID, len(groupInfo.Participants))
590
+ lidPairs := make([]store.LIDMapping, len(groupInfo.Participants))
591
+ redactedPhones := make([]store.RedactedPhoneEntry, 0)
592
+ for i, part := range groupInfo.Participants {
593
+ participants[i] = part.JID
594
+ if !part.PhoneNumber.IsEmpty() && !part.LID.IsEmpty() {
595
+ lidPairs[i] = store.LIDMapping{
596
+ LID: part.LID,
597
+ PN: part.PhoneNumber,
598
+ }
599
+ }
600
+ if part.DisplayName != "" && !part.LID.IsEmpty() {
601
+ redactedPhones = append(redactedPhones, store.RedactedPhoneEntry{
602
+ JID: part.LID,
603
+ RedactedPhone: part.DisplayName,
604
+ })
605
+ }
606
+ }
607
+ if lock {
608
+ cli.groupCacheLock.Lock()
609
+ defer cli.groupCacheLock.Unlock()
610
+ }
611
+ cli.groupCache[groupInfo.JID] = &groupMetaCache{
612
+ AddressingMode: groupInfo.AddressingMode,
613
+ CommunityAnnouncementGroup: groupInfo.IsAnnounce && groupInfo.IsDefaultSubGroup,
614
+ Members: participants,
615
+ }
616
+ return lidPairs, redactedPhones
617
+ }
618
+
575
619
  func (cli *Client) getGroupInfo(ctx context.Context, jid types.JID, lockParticipantCache bool) (*types.GroupInfo, error) {
576
620
  res, err := cli.sendGroupIQ(ctx, iqGet, jid, waBinary.Node{
577
621
  Tag: "query",
@@ -593,30 +637,15 @@ func (cli *Client) getGroupInfo(ctx context.Context, jid types.JID, lockParticip
593
637
  if err != nil {
594
638
  return groupInfo, err
595
639
  }
596
- if lockParticipantCache {
597
- cli.groupCacheLock.Lock()
598
- defer cli.groupCacheLock.Unlock()
599
- }
600
- participants := make([]types.JID, len(groupInfo.Participants))
601
- lidPairs := make([]store.LIDMapping, len(groupInfo.Participants))
602
- for i, part := range groupInfo.Participants {
603
- participants[i] = part.JID
604
- if !part.PhoneNumber.IsEmpty() && !part.LID.IsEmpty() {
605
- lidPairs[i] = store.LIDMapping{
606
- LID: part.LID,
607
- PN: part.PhoneNumber,
608
- }
609
- }
610
- }
611
- cli.groupCache[jid] = &groupMetaCache{
612
- AddressingMode: groupInfo.AddressingMode,
613
- CommunityAnnouncementGroup: groupInfo.IsAnnounce && groupInfo.IsDefaultSubGroup,
614
- Members: participants,
615
- }
640
+ lidPairs, redactedPhones := cli.cacheGroupInfo(groupInfo, lockParticipantCache)
616
641
  err = cli.Store.LIDs.PutManyLIDMappings(ctx, lidPairs)
617
642
  if err != nil {
618
643
  cli.Log.Warnf("Failed to store LID mappings for members of %s: %v", jid, err)
619
644
  }
645
+ err = cli.Store.Contacts.PutManyRedactedPhones(ctx, redactedPhones)
646
+ if err != nil {
647
+ cli.Log.Warnf("Failed to store redacted phones for members of %s: %v", jid, err)
648
+ }
620
649
  return groupInfo, nil
621
650
  }
622
651
 
@@ -670,8 +699,8 @@ func (cli *Client) parseGroupNode(groupNode *waBinary.Node) (*types.GroupInfo, e
670
699
  group.OwnerJID = ag.OptionalJIDOrEmpty("creator")
671
700
  group.OwnerPN = ag.OptionalJIDOrEmpty("creator_pn")
672
701
 
673
- group.Name = ag.String("subject")
674
- group.NameSetAt = ag.UnixTime("s_t")
702
+ group.Name = ag.OptionalString("subject")
703
+ group.NameSetAt = ag.OptionalUnixTime("s_t")
675
704
  group.NameSetBy = ag.OptionalJIDOrEmpty("s_o")
676
705
  group.NameSetByPN = ag.OptionalJIDOrEmpty("s_o_pn")
677
706
 
@@ -738,8 +767,8 @@ func parseGroupLinkTargetNode(groupNode *waBinary.Node) (types.GroupLinkTarget,
738
767
  return types.GroupLinkTarget{
739
768
  JID: jidKey,
740
769
  GroupName: types.GroupName{
741
- Name: ag.String("subject"),
742
- NameSetAt: ag.UnixTime("s_t"),
770
+ Name: ag.OptionalString("subject"),
771
+ NameSetAt: ag.OptionalUnixTime("s_t"),
743
772
  },
744
773
  GroupIsDefaultSub: types.GroupIsDefaultSub{
745
774
  IsDefaultSubGroup: groupNode.GetChildByTag("default_sub_group").Tag == "default_sub_group",
@@ -777,10 +806,10 @@ func parseParticipantList(node *waBinary.Node) (participants []types.JID, lidPai
777
806
  return
778
807
  }
779
808
 
780
- func (cli *Client) parseGroupCreate(parentNode, node *waBinary.Node) (*events.JoinedGroup, []store.LIDMapping, error) {
809
+ func (cli *Client) parseGroupCreate(parentNode, node *waBinary.Node) (*events.JoinedGroup, []store.LIDMapping, []store.RedactedPhoneEntry, error) {
781
810
  groupNode, ok := node.GetOptionalChildByTag("group")
782
811
  if !ok {
783
- return nil, nil, fmt.Errorf("group create notification didn't contain group info")
812
+ return nil, nil, nil, fmt.Errorf("group create notification didn't contain group info")
784
813
  }
785
814
  var evt events.JoinedGroup
786
815
  pag := parentNode.AttrGetter()
@@ -793,19 +822,11 @@ func (cli *Client) parseGroupCreate(parentNode, node *waBinary.Node) (*events.Jo
793
822
  evt.Notify = pag.OptionalString("notify")
794
823
  info, err := cli.parseGroupNode(&groupNode)
795
824
  if err != nil {
796
- return nil, nil, fmt.Errorf("failed to parse group info in create notification: %w", err)
825
+ return nil, nil, nil, fmt.Errorf("failed to parse group info in create notification: %w", err)
797
826
  }
798
827
  evt.GroupInfo = *info
799
- lidPairs := make([]store.LIDMapping, 0, len(info.Participants))
800
- for _, pcp := range info.Participants {
801
- if !pcp.PhoneNumber.IsEmpty() && !pcp.LID.IsEmpty() {
802
- lidPairs = append(lidPairs, store.LIDMapping{
803
- LID: pcp.LID,
804
- PN: pcp.PhoneNumber,
805
- })
806
- }
807
- }
808
- return &evt, lidPairs, nil
828
+ lidPairs, redactedPhones := cli.cacheGroupInfo(info, true)
829
+ return &evt, lidPairs, redactedPhones, nil
809
830
  }
810
831
 
811
832
  func (cli *Client) parseGroupChange(node *waBinary.Node) (*events.GroupInfo, []store.LIDMapping, error) {
@@ -965,17 +986,17 @@ Outer:
965
986
  }
966
987
  }
967
988
 
968
- func (cli *Client) parseGroupNotification(node *waBinary.Node) (any, []store.LIDMapping, error) {
989
+ func (cli *Client) parseGroupNotification(node *waBinary.Node) (any, []store.LIDMapping, []store.RedactedPhoneEntry, error) {
969
990
  children := node.GetChildren()
970
991
  if len(children) == 1 && children[0].Tag == "create" {
971
992
  return cli.parseGroupCreate(node, &children[0])
972
993
  } else {
973
994
  groupChange, lidPairs, err := cli.parseGroupChange(node)
974
995
  if err != nil {
975
- return nil, nil, err
996
+ return nil, nil, nil, err
976
997
  }
977
998
  cli.updateGroupParticipantCache(groupChange)
978
- return groupChange, lidPairs, nil
999
+ return groupChange, lidPairs, nil, nil
979
1000
  }
980
1001
  }
981
1002
 
@@ -67,7 +67,7 @@ func (int *DangerousInternalClient) RequestAppStateKeys(ctx context.Context, raw
67
67
  int.c.requestAppStateKeys(ctx, rawKeyIDs)
68
68
  }
69
69
 
70
- func (int *DangerousInternalClient) HandleDecryptedArmadillo(ctx context.Context, info *types.MessageInfo, decrypted []byte, retryCount int) (handled, handlerFailed bool) {
70
+ func (int *DangerousInternalClient) HandleDecryptedArmadillo(ctx context.Context, info *types.MessageInfo, decrypted []byte, retryCount int) (handlerFailed bool) {
71
71
  return int.c.handleDecryptedArmadillo(ctx, info, decrypted, retryCount)
72
72
  }
73
73
 
@@ -207,6 +207,10 @@ func (int *DangerousInternalClient) SendGroupIQ(ctx context.Context, iqType info
207
207
  return int.c.sendGroupIQ(ctx, iqType, jid, content)
208
208
  }
209
209
 
210
+ func (int *DangerousInternalClient) CacheGroupInfo(groupInfo *types.GroupInfo, lock bool) ([]store.LIDMapping, []store.RedactedPhoneEntry) {
211
+ return int.c.cacheGroupInfo(groupInfo, lock)
212
+ }
213
+
210
214
  func (int *DangerousInternalClient) GetGroupInfo(ctx context.Context, jid types.JID, lockParticipantCache bool) (*types.GroupInfo, error) {
211
215
  return int.c.getGroupInfo(ctx, jid, lockParticipantCache)
212
216
  }
@@ -219,7 +223,7 @@ func (int *DangerousInternalClient) ParseGroupNode(groupNode *waBinary.Node) (*t
219
223
  return int.c.parseGroupNode(groupNode)
220
224
  }
221
225
 
222
- func (int *DangerousInternalClient) ParseGroupCreate(parentNode, node *waBinary.Node) (*events.JoinedGroup, []store.LIDMapping, error) {
226
+ func (int *DangerousInternalClient) ParseGroupCreate(parentNode, node *waBinary.Node) (*events.JoinedGroup, []store.LIDMapping, []store.RedactedPhoneEntry, error) {
223
227
  return int.c.parseGroupCreate(parentNode, node)
224
228
  }
225
229
 
@@ -231,7 +235,7 @@ func (int *DangerousInternalClient) UpdateGroupParticipantCache(evt *events.Grou
231
235
  int.c.updateGroupParticipantCache(evt)
232
236
  }
233
237
 
234
- func (int *DangerousInternalClient) ParseGroupNotification(node *waBinary.Node) (any, []store.LIDMapping, error) {
238
+ func (int *DangerousInternalClient) ParseGroupNotification(node *waBinary.Node) (any, []store.LIDMapping, []store.RedactedPhoneEntry, error) {
235
239
  return int.c.parseGroupNotification(node)
236
240
  }
237
241
 
@@ -287,8 +291,8 @@ func (int *DangerousInternalClient) MigrateSessionStore(ctx context.Context, pn,
287
291
  int.c.migrateSessionStore(ctx, pn, lid)
288
292
  }
289
293
 
290
- func (int *DangerousInternalClient) DecryptMessages(ctx context.Context, info *types.MessageInfo, node *waBinary.Node) (handlerFailed bool) {
291
- return int.c.decryptMessages(ctx, info, node)
294
+ func (int *DangerousInternalClient) DecryptMessages(ctx context.Context, info *types.MessageInfo, node *waBinary.Node) {
295
+ int.c.decryptMessages(ctx, info, node)
292
296
  }
293
297
 
294
298
  func (int *DangerousInternalClient) ClearUntrustedIdentity(ctx context.Context, target types.JID) error {
@@ -651,16 +655,16 @@ func (int *DangerousInternalClient) MakeDeviceIdentityNode() waBinary.Node {
651
655
  return int.c.makeDeviceIdentityNode()
652
656
  }
653
657
 
654
- func (int *DangerousInternalClient) EncryptMessageForDevices(ctx context.Context, allDevices []types.JID, id string, msgPlaintext, dsmPlaintext []byte, encAttrs waBinary.Attrs) ([]waBinary.Node, bool) {
658
+ func (int *DangerousInternalClient) EncryptMessageForDevices(ctx context.Context, allDevices []types.JID, id string, msgPlaintext, dsmPlaintext []byte, encAttrs waBinary.Attrs) ([]waBinary.Node, bool, error) {
655
659
  return int.c.encryptMessageForDevices(ctx, allDevices, id, msgPlaintext, dsmPlaintext, encAttrs)
656
660
  }
657
661
 
658
- func (int *DangerousInternalClient) EncryptMessageForDeviceAndWrap(ctx context.Context, plaintext []byte, wireIdentity, encryptionIdentity types.JID, bundle *prekey.Bundle, encAttrs waBinary.Attrs) (*waBinary.Node, bool, error) {
659
- return int.c.encryptMessageForDeviceAndWrap(ctx, plaintext, wireIdentity, encryptionIdentity, bundle, encAttrs)
662
+ func (int *DangerousInternalClient) EncryptMessageForDeviceAndWrap(ctx context.Context, plaintext []byte, wireIdentity, encryptionIdentity types.JID, bundle *prekey.Bundle, encAttrs waBinary.Attrs, existingSessions map[string]bool) (*waBinary.Node, bool, error) {
663
+ return int.c.encryptMessageForDeviceAndWrap(ctx, plaintext, wireIdentity, encryptionIdentity, bundle, encAttrs, existingSessions)
660
664
  }
661
665
 
662
- func (int *DangerousInternalClient) EncryptMessageForDevice(ctx context.Context, plaintext []byte, to types.JID, bundle *prekey.Bundle, extraAttrs waBinary.Attrs) (*waBinary.Node, bool, error) {
663
- return int.c.encryptMessageForDevice(ctx, plaintext, to, bundle, extraAttrs)
666
+ func (int *DangerousInternalClient) EncryptMessageForDevice(ctx context.Context, plaintext []byte, to types.JID, bundle *prekey.Bundle, extraAttrs waBinary.Attrs, existingSessions map[string]bool) (*waBinary.Node, bool, error) {
667
+ return int.c.encryptMessageForDevice(ctx, plaintext, to, bundle, extraAttrs, existingSessions)
664
668
  }
665
669
 
666
670
  func (int *DangerousInternalClient) RawUpload(ctx context.Context, dataToUpload io.Reader, uploadSize uint64, fileHash []byte, appInfo MediaType, newsletter bool, resp *UploadResponse) error {
@@ -57,12 +57,12 @@ func (cli *Client) handleEncryptedMessage(node *waBinary.Node) {
57
57
  if len(info.PushName) > 0 && info.PushName != "-" && (cli.MessengerConfig == nil || info.PushName != "username") {
58
58
  go cli.updatePushName(cli.BackgroundEventCtx, info.Sender, info, info.PushName)
59
59
  }
60
- var cancelled bool
61
- defer cli.maybeDeferredAck(ctx, node)(&cancelled)
62
60
  if info.Sender.Server == types.NewsletterServer {
61
+ var cancelled bool
62
+ defer cli.maybeDeferredAck(ctx, node)(&cancelled)
63
63
  cancelled = cli.handlePlaintextMessage(ctx, info, node)
64
64
  } else {
65
- cancelled = cli.decryptMessages(ctx, info, node)
65
+ cli.decryptMessages(ctx, info, node)
66
66
  }
67
67
  }
68
68
  }
@@ -95,6 +95,29 @@ func (cli *Client) parseMessageSource(node *waBinary.Node, requireParticipant bo
95
95
  }
96
96
  if from.Server == types.BroadcastServer {
97
97
  source.BroadcastListOwner = ag.OptionalJIDOrEmpty("recipient")
98
+ participants, ok := node.GetOptionalChildByTag("participants")
99
+ if ok && source.IsFromMe {
100
+ children := participants.GetChildren()
101
+ source.BroadcastRecipients = make([]types.BroadcastRecipient, 0, len(children))
102
+ for _, child := range children {
103
+ if child.Tag != "to" {
104
+ continue
105
+ }
106
+ cag := child.AttrGetter()
107
+ mainJID := cag.JID("jid")
108
+ if mainJID.Server == types.HiddenUserServer {
109
+ source.BroadcastRecipients = append(source.BroadcastRecipients, types.BroadcastRecipient{
110
+ LID: mainJID,
111
+ PN: cag.OptionalJIDOrEmpty("peer_recipient_pn"),
112
+ })
113
+ } else {
114
+ source.BroadcastRecipients = append(source.BroadcastRecipients, types.BroadcastRecipient{
115
+ LID: cag.OptionalJIDOrEmpty("peer_recipient_lid"),
116
+ PN: mainJID,
117
+ })
118
+ }
119
+ }
120
+ }
98
121
  }
99
122
  } else if from.Server == types.NewsletterServer {
100
123
  source.Chat = from
@@ -263,15 +286,17 @@ func (cli *Client) migrateSessionStore(ctx context.Context, pn, lid types.JID) {
263
286
  }
264
287
  }
265
288
 
266
- func (cli *Client) decryptMessages(ctx context.Context, info *types.MessageInfo, node *waBinary.Node) (handlerFailed bool) {
289
+ func (cli *Client) decryptMessages(ctx context.Context, info *types.MessageInfo, node *waBinary.Node) {
267
290
  unavailableNode, ok := node.GetOptionalChildByTag("unavailable")
268
291
  if ok && len(node.GetChildrenByTag("enc")) == 0 {
269
292
  uType := events.UnavailableType(unavailableNode.AttrGetter().String("type"))
270
293
  cli.Log.Warnf("Unavailable message %s from %s (type: %q)", info.ID, info.SourceString(), uType)
271
294
  if cli.SynchronousAck {
272
295
  cli.immediateRequestMessageFromPhone(ctx, info)
296
+ cli.sendAck(node)
273
297
  } else {
274
298
  go cli.delayedRequestMessageFromPhone(info)
299
+ go cli.sendAck(node)
275
300
  }
276
301
  cli.dispatchEvent(&events.UndecryptableMessage{Info: *info, IsUnavailable: true, UnavailableType: uType})
277
302
  return
@@ -279,7 +304,6 @@ func (cli *Client) decryptMessages(ctx context.Context, info *types.MessageInfo,
279
304
 
280
305
  children := node.GetChildren()
281
306
  cli.Log.Debugf("Decrypting message from %s", info.SourceString())
282
- handled := false
283
307
  containsDirectMsg := false
284
308
  senderEncryptionJID := info.Sender
285
309
  if info.Sender.Server == types.DefaultUserServer && !info.Sender.IsBot() {
@@ -346,22 +370,19 @@ func (cli *Client) decryptMessages(ctx context.Context, info *types.MessageInfo,
346
370
 
347
371
  if errors.Is(err, EventAlreadyProcessed) {
348
372
  cli.Log.Debugf("Ignoring message %s from %s: %v", info.ID, info.SourceString(), err)
349
- return
373
+ continue
350
374
  } else if err != nil {
351
375
  cli.Log.Warnf("Error decrypting message %s from %s: %v", info.ID, info.SourceString(), err)
352
376
  if ctx.Err() != nil || errors.Is(err, context.Canceled) {
353
- handlerFailed = true
354
377
  return
355
378
  }
356
379
  isUnavailable := encType == "skmsg" && !containsDirectMsg && errors.Is(err, signalerror.ErrNoSenderKeyForUser)
357
- if encType != "msmsg" {
358
- if cli.SynchronousAck {
359
- cli.sendRetryReceipt(ctx, node, info, isUnavailable)
360
- } else {
361
- go cli.sendRetryReceipt(context.WithoutCancel(ctx), node, info, isUnavailable)
362
- }
380
+ if cli.SynchronousAck {
381
+ cli.sendRetryReceipt(ctx, node, info, isUnavailable)
382
+ } else {
383
+ go cli.sendRetryReceipt(context.WithoutCancel(ctx), node, info, isUnavailable)
363
384
  }
364
- handlerFailed = cli.dispatchEvent(&events.UndecryptableMessage{
385
+ cli.dispatchEvent(&events.UndecryptableMessage{
365
386
  Info: *info,
366
387
  IsUnavailable: isUnavailable,
367
388
  DecryptFailMode: events.DecryptFailMode(ag.OptionalString("decrypt-fail")),
@@ -372,33 +393,37 @@ func (cli *Client) decryptMessages(ctx context.Context, info *types.MessageInfo,
372
393
  cli.cancelDelayedRequestFromPhone(info.ID)
373
394
 
374
395
  var msg waE2E.Message
396
+ var handlerFailed bool
375
397
  switch ag.Int("v") {
376
398
  case 2:
399
+ // TODO send nack instead of receipt for proto unmarshal errors (both this one and armadillo)
377
400
  err = proto.Unmarshal(decrypted, &msg)
378
401
  if err != nil {
379
402
  cli.Log.Warnf("Error unmarshaling decrypted message from %s: %v", info.SourceString(), err)
380
403
  continue
381
404
  }
382
405
  handlerFailed = cli.handleDecryptedMessage(ctx, info, &msg, retryCount)
383
- handled = true
384
406
  case 3:
385
- handled, handlerFailed = cli.handleDecryptedArmadillo(ctx, info, decrypted, retryCount)
407
+ handlerFailed = cli.handleDecryptedArmadillo(ctx, info, decrypted, retryCount)
386
408
  default:
387
409
  cli.Log.Warnf("Unknown version %d in decrypted message from %s", ag.Int("v"), info.SourceString())
388
410
  }
389
411
  if handlerFailed {
390
412
  cli.Log.Warnf("Handler for %s failed", info.ID)
413
+ return
391
414
  }
392
- if ciphertextHash != nil && cli.EnableDecryptedEventBuffer && !handlerFailed {
415
+ if ciphertextHash != nil && cli.EnableDecryptedEventBuffer {
393
416
  // Use the context passed to decryptMessages
394
417
  err = cli.Store.EventBuffer.ClearBufferedEventPlaintext(ctx, *ciphertextHash)
395
418
  if err != nil {
396
419
  zerolog.Ctx(ctx).Err(err).
397
420
  Hex("ciphertext_hash", ciphertextHash[:]).
421
+ Str("message_id", info.ID).
398
422
  Msg("Failed to clear buffered event plaintext")
399
423
  } else {
400
424
  zerolog.Ctx(ctx).Debug().
401
425
  Hex("ciphertext_hash", ciphertextHash[:]).
426
+ Str("message_id", info.ID).
402
427
  Msg("Deleted event plaintext from buffer")
403
428
  }
404
429
 
@@ -413,7 +438,9 @@ func (cli *Client) decryptMessages(ctx context.Context, info *types.MessageInfo,
413
438
  }
414
439
  }
415
440
  }
416
- if handled && !handlerFailed {
441
+ if cli.SynchronousAck {
442
+ cli.sendMessageReceipt(info)
443
+ } else {
417
444
  go cli.sendMessageReceipt(info)
418
445
  }
419
446
  return
@@ -231,6 +231,29 @@ func (cli *Client) DecryptPollVote(ctx context.Context, vote *events.Message) (*
231
231
  return &msg, nil
232
232
  }
233
233
 
234
+ func (cli *Client) DecryptSecretEncryptedMessage(ctx context.Context, evt *events.Message) (*waE2E.Message, error) {
235
+ encMessage := evt.Message.GetSecretEncryptedMessage()
236
+ if encMessage == nil {
237
+ return nil, ErrNotSecretEncryptedMessage
238
+ }
239
+ if encMessage.GetSecretEncType() != waE2E.SecretEncryptedMessage_EVENT_EDIT {
240
+ return nil, fmt.Errorf("unsupported secret enc type: %s", encMessage.SecretEncType.String())
241
+ }
242
+ plaintext, err := cli.decryptMsgSecret(ctx, evt, EncSecretEventEdit, encMessage, encMessage.GetTargetMessageKey())
243
+ if err != nil {
244
+ return nil, fmt.Errorf("failed to decrypt message: %w", err)
245
+ }
246
+ var msg waE2E.Message
247
+ err = proto.Unmarshal(plaintext, &msg)
248
+ if err != nil {
249
+ return nil, fmt.Errorf("failed to decode message protobuf: %w", err)
250
+ }
251
+ if evt.Message.MessageContextInfo != nil && msg.MessageContextInfo == nil {
252
+ msg.MessageContextInfo = evt.Message.MessageContextInfo
253
+ }
254
+ return &msg, nil
255
+ }
256
+
234
257
  func getKeyFromInfo(msgInfo *types.MessageInfo) *waCommon.MessageKey {
235
258
  creationKey := &waCommon.MessageKey{
236
259
  RemoteJID: proto.String(msgInfo.Chat.String()),
@@ -430,7 +430,7 @@ func (cli *Client) handleNotification(node *waBinary.Node) {
430
430
  case "fbid:devices":
431
431
  cli.handleFBDeviceNotification(ctx, node)
432
432
  case "w:gp2":
433
- evt, lidPairs, err := cli.parseGroupNotification(node)
433
+ evt, lidPairs, redactedPhones, err := cli.parseGroupNotification(node)
434
434
  if err != nil {
435
435
  cli.Log.Errorf("Failed to parse group notification: %v", err)
436
436
  } else {
@@ -438,6 +438,10 @@ func (cli *Client) handleNotification(node *waBinary.Node) {
438
438
  if err != nil {
439
439
  cli.Log.Errorf("Failed to store LID mappings from group notification: %v", err)
440
440
  }
441
+ err = cli.Store.Contacts.PutManyRedactedPhones(ctx, redactedPhones)
442
+ if err != nil {
443
+ cli.Log.Warnf("Failed to store redacted phones from group notification: %v", err)
444
+ }
441
445
  cancelled = cli.dispatchEvent(evt)
442
446
  }
443
447
  case "picture":
@@ -134,7 +134,7 @@ func (cli *Client) handlePair(ctx context.Context, deviceIdentityBytes []byte, r
134
134
  return &PairProtoError{"failed to parse signed device identity in pair success message", err}
135
135
  }
136
136
 
137
- if !verifyDeviceIdentityAccountSignature(&deviceIdentity, cli.Store.IdentityKey, isHostedAccount) {
137
+ if !verifyDeviceIdentityAccountSignature(&deviceIdentity, cli.Store.IdentityKey) {
138
138
  cli.sendPairError(reqID, 401, "signature-mismatch")
139
139
  return ErrPairInvalidDeviceSignature
140
140
  }
@@ -224,7 +224,7 @@ func concatBytes(data ...[]byte) []byte {
224
224
  return output
225
225
  }
226
226
 
227
- func verifyDeviceIdentityAccountSignature(deviceIdentity *waAdv.ADVSignedDeviceIdentity, ikp *keys.KeyPair, isHostedAccount bool) bool {
227
+ func verifyDeviceIdentityAccountSignature(deviceIdentity *waAdv.ADVSignedDeviceIdentity, ikp *keys.KeyPair) bool {
228
228
  if len(deviceIdentity.AccountSignatureKey) != 32 || len(deviceIdentity.AccountSignature) != 64 {
229
229
  return false
230
230
  }
@@ -232,11 +232,7 @@ func verifyDeviceIdentityAccountSignature(deviceIdentity *waAdv.ADVSignedDeviceI
232
232
  signatureKey := ecc.NewDjbECPublicKey(*(*[32]byte)(deviceIdentity.AccountSignatureKey))
233
233
  signature := *(*[64]byte)(deviceIdentity.AccountSignature)
234
234
 
235
- prefix := AdvPrefixAccountSignature
236
- if isHostedAccount {
237
- prefix = AdvHostedPrefixDeviceIdentityAccountSignature
238
- }
239
- message := concatBytes(prefix, deviceIdentity.Details, ikp.Pub[:])
235
+ message := concatBytes(AdvPrefixAccountSignature, deviceIdentity.Details, ikp.Pub[:])
240
236
  return ecc.VerifySignature(signatureKey, message, signature)
241
237
  }
242
238